diff --git a/bacnet-stack/demo/handler/client.h b/bacnet-stack/demo/handler/client.h index ea639134..c9e77f37 100644 --- a/bacnet-stack/demo/handler/client.h +++ b/bacnet-stack/demo/handler/client.h @@ -35,63 +35,45 @@ #ifdef __cplusplus extern "C" { -#endif /* __cplusplus */ +#endif /* __cplusplus */ /* unconfirmed requests */ -void Send_WhoIs( - int32_t low_limit, - int32_t high_limit); + void Send_WhoIs(int32_t low_limit, int32_t high_limit); -void Send_WhoHas_Object( - int32_t low_limit, - int32_t high_limit, - BACNET_OBJECT_TYPE object_type, - uint32_t object_instance); + void Send_WhoHas_Object(int32_t low_limit, + int32_t high_limit, + BACNET_OBJECT_TYPE object_type, uint32_t object_instance); -void Send_WhoHas_Name( - int32_t low_limit, - int32_t high_limit, - char *object_name); + void Send_WhoHas_Name(int32_t low_limit, + int32_t high_limit, char *object_name); -void Send_I_Have( - uint32_t device_id, - BACNET_OBJECT_TYPE object_type, - uint32_t object_instance, - char *object_name); - -/* returns the invoke ID for confirmed request, or 0 if failed */ -uint8_t Send_Read_Property_Request( - uint32_t device_id, /* destination device */ - BACNET_OBJECT_TYPE object_type, - uint32_t object_instance, - BACNET_PROPERTY_ID object_property, - int32_t array_index); + void Send_I_Have(uint32_t device_id, + BACNET_OBJECT_TYPE object_type, + uint32_t object_instance, char *object_name); /* returns the invoke ID for confirmed request, or 0 if failed */ -uint8_t Send_Write_Property_Request( - uint32_t device_id, // destination device - BACNET_OBJECT_TYPE object_type, - uint32_t object_instance, - BACNET_PROPERTY_ID object_property, - BACNET_APPLICATION_DATA_VALUE *object_value, - uint8_t priority, - int32_t array_index); + uint8_t Send_Read_Property_Request(uint32_t device_id, /* destination device */ + BACNET_OBJECT_TYPE object_type, + uint32_t object_instance, + BACNET_PROPERTY_ID object_property, int32_t array_index); /* returns the invoke ID for confirmed request, or 0 if failed */ -uint8_t Send_Reinitialize_Device_Request( - uint32_t device_id, - BACNET_REINITIALIZED_STATE state, - char *password); + uint8_t Send_Write_Property_Request(uint32_t device_id, // destination device + BACNET_OBJECT_TYPE object_type, + uint32_t object_instance, + BACNET_PROPERTY_ID object_property, + BACNET_APPLICATION_DATA_VALUE * object_value, + uint8_t priority, int32_t array_index); /* returns the invoke ID for confirmed request, or 0 if failed */ -uint8_t Send_Device_Communication_Control_Request( - uint32_t device_id, - uint16_t timeDuration, /* 0=optional */ - BACNET_COMMUNICATION_ENABLE_DISABLE state, - char *password); /* NULL=optional */ - + uint8_t Send_Reinitialize_Device_Request(uint32_t device_id, + BACNET_REINITIALIZED_STATE state, char *password); + +/* returns the invoke ID for confirmed request, or 0 if failed */ + uint8_t Send_Device_Communication_Control_Request(uint32_t device_id, uint16_t timeDuration, /* 0=optional */ + BACNET_COMMUNICATION_ENABLE_DISABLE state, char *password); /* NULL=optional */ + #ifdef __cplusplus } -#endif /* __cplusplus */ - +#endif /* __cplusplus */ #endif diff --git a/bacnet-stack/demo/handler/h_arf.c b/bacnet-stack/demo/handler/h_arf.c index 8cb28c06..c9fe3a1f 100644 --- a/bacnet-stack/demo/handler/h_arf.c +++ b/bacnet-stack/demo/handler/h_arf.c @@ -41,116 +41,82 @@ #include "ao.h" #include "bacfile.h" -void handler_atomic_read_file( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_DATA *service_data) +void handler_atomic_read_file(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, BACNET_CONFIRMED_SERVICE_DATA * service_data) { - BACNET_ATOMIC_READ_FILE_DATA data; - int len = 0; - int pdu_len = 0; - BACNET_ADDRESS my_address; - bool send = false; - bool error = false; - int bytes_sent = 0; - BACNET_ERROR_CLASS error_class = ERROR_CLASS_OBJECT; - BACNET_ERROR_CODE error_code = ERROR_CODE_UNKNOWN_OBJECT; + BACNET_ATOMIC_READ_FILE_DATA data; + int len = 0; + int pdu_len = 0; + BACNET_ADDRESS my_address; + bool send = false; + bool error = false; + int bytes_sent = 0; + BACNET_ERROR_CLASS error_class = ERROR_CLASS_OBJECT; + BACNET_ERROR_CODE error_code = ERROR_CODE_UNKNOWN_OBJECT; - fprintf(stderr,"Received Atomic-Read-File Request!\n"); - len = arf_decode_service_request( - service_request, - service_len, - &data); - if (len < 0) - fprintf(stderr,"Unable to decode Atomic-Read-File Request!\n"); - // prepare a reply - datalink_get_my_address(&my_address); - // encode the NPDU portion of the packet - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - src, - &my_address, - false, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); - // bad decoding - send an abort - if (len < 0) - { - pdu_len += abort_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - ABORT_REASON_OTHER); - fprintf(stderr,"Sending Abort!\n"); - send = true; - } - else if (service_data->segmented_message) - { - pdu_len += abort_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); - fprintf(stderr,"Sending Abort!\n"); - send = true; - } - else - { - if (data.access == FILE_STREAM_ACCESS) - { - if (data.type.stream.requestedOctetCount < - octetstring_capacity(&data.fileData)) - { - if (bacfile_read_data(&data)) - { - pdu_len += arf_ack_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - &data); - send = true; - } - else - { - send = true; - error = true; - } - } - else - { - pdu_len += abort_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); - fprintf(stderr,"Sending Abort!\n"); + fprintf(stderr, "Received Atomic-Read-File Request!\n"); + len = arf_decode_service_request(service_request, service_len, &data); + if (len < 0) + fprintf(stderr, "Unable to decode Atomic-Read-File Request!\n"); + // prepare a reply + datalink_get_my_address(&my_address); + // encode the NPDU portion of the packet + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], src, &my_address, false, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); + // bad decoding - send an abort + if (len < 0) { + pdu_len += abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, ABORT_REASON_OTHER); + fprintf(stderr, "Sending Abort!\n"); send = true; - } + } else if (service_data->segmented_message) { + pdu_len += abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); + fprintf(stderr, "Sending Abort!\n"); + send = true; + } else { + if (data.access == FILE_STREAM_ACCESS) { + if (data.type.stream.requestedOctetCount < + octetstring_capacity(&data.fileData)) { + if (bacfile_read_data(&data)) { + pdu_len += + arf_ack_encode_apdu(&Handler_Transmit_Buffer + [pdu_len], service_data->invoke_id, &data); + send = true; + } else { + send = true; + error = true; + } + } else { + pdu_len += + abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); + fprintf(stderr, "Sending Abort!\n"); + send = true; + } + } else { + error_class = ERROR_CLASS_SERVICES; + error_code = ERROR_CODE_INVALID_FILE_ACCESS_METHOD; + send = true; + error = true; + } } - else - { - error_class = ERROR_CLASS_SERVICES; - error_code = ERROR_CODE_INVALID_FILE_ACCESS_METHOD; - send = true; - error = true; + if (error) { + pdu_len += bacerror_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + SERVICE_CONFIRMED_ATOMIC_READ_FILE, error_class, error_code); + fprintf(stderr, "Sending Error!\n"); + send = true; + } + if (send) { + bytes_sent = datalink_send_pdu(src, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, "Failed to send PDU (%s)!\n", strerror(errno)); } - } - if (error) - { - pdu_len += bacerror_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - SERVICE_CONFIRMED_ATOMIC_READ_FILE, - error_class, - error_code); - fprintf(stderr,"Sending Error!\n"); - send = true; - } - if (send) - { - bytes_sent = datalink_send_pdu( - src, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to send PDU (%s)!\n", strerror(errno)); - } - return; + return; } diff --git a/bacnet-stack/demo/handler/h_arf_a.c b/bacnet-stack/demo/handler/h_arf_a.c index ccff7a59..933cc091 100644 --- a/bacnet-stack/demo/handler/h_arf_a.c +++ b/bacnet-stack/demo/handler/h_arf_a.c @@ -47,54 +47,42 @@ // that someone can read from us. It is common to // use the description as the file name. #if BACFILE -void handler_atomic_read_file_ack( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_ACK_DATA *service_data) +void handler_atomic_read_file_ack(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, BACNET_CONFIRMED_SERVICE_ACK_DATA * service_data) { - int len = 0; - BACNET_ATOMIC_READ_FILE_DATA data; - FILE *pFile = NULL; - char *pFilename = NULL; - uint32_t instance = 0; + int len = 0; + BACNET_ATOMIC_READ_FILE_DATA data; + FILE *pFile = NULL; + char *pFilename = NULL; + uint32_t instance = 0; - (void)src; - // get the file instance from the tsm data before freeing it - instance = bacfile_instance_from_tsm(service_data->invoke_id); - len = arf_ack_decode_service_request( - service_request, - service_len, - &data); - fprintf(stderr,"Received Read-File Ack!\n"); - if ((len > 0) && (instance <= BACNET_MAX_INSTANCE)) - { - // write the data received to the file specified - if (data.access == FILE_STREAM_ACCESS) - { - pFilename = bacfile_name(instance); - if (pFilename) - { - pFile = fopen(pFilename, "rb"); - if (pFile) - { - (void)fseek(pFile, - data.type.stream.fileStartPosition, - SEEK_SET); - if (fwrite(octetstring_value(&data.fileData), - octetstring_length(&data.fileData),1,pFile) != 1) - fprintf(stderr,"Failed to write to %s (%u)!\n", - pFilename, instance); - fclose(pFile); + (void) src; + // get the file instance from the tsm data before freeing it + instance = bacfile_instance_from_tsm(service_data->invoke_id); + len = arf_ack_decode_service_request(service_request, + service_len, &data); + fprintf(stderr, "Received Read-File Ack!\n"); + if ((len > 0) && (instance <= BACNET_MAX_INSTANCE)) { + // write the data received to the file specified + if (data.access == FILE_STREAM_ACCESS) { + pFilename = bacfile_name(instance); + if (pFilename) { + pFile = fopen(pFilename, "rb"); + if (pFile) { + (void) fseek(pFile, + data.type.stream.fileStartPosition, SEEK_SET); + if (fwrite(octetstring_value(&data.fileData), + octetstring_length(&data.fileData), 1, + pFile) != 1) + fprintf(stderr, "Failed to write to %s (%u)!\n", + pFilename, instance); + fclose(pFile); + } + } + } else if (data.access == FILE_RECORD_ACCESS) { + // FIXME: add handling for Record Access } - } } - else if (data.access == FILE_RECORD_ACCESS) - { - // FIXME: add handling for Record Access - } - } } #endif - - diff --git a/bacnet-stack/demo/handler/h_dcc.c b/bacnet-stack/demo/handler/h_dcc.c index a9943f08..d93488a4 100644 --- a/bacnet-stack/demo/handler/h_dcc.c +++ b/bacnet-stack/demo/handler/h_dcc.c @@ -40,106 +40,76 @@ static char *My_Password = "AnnaRoseKarg"; -void handler_device_communication_control( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_DATA *service_data) +void handler_device_communication_control(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, BACNET_CONFIRMED_SERVICE_DATA * service_data) { - uint16_t timeDuration = 0; - BACNET_COMMUNICATION_ENABLE_DISABLE state = COMMUNICATION_ENABLE; - BACNET_CHARACTER_STRING password; - int len = 0; - int pdu_len = 0; - BACNET_ADDRESS my_address; - int bytes_sent = 0; + uint16_t timeDuration = 0; + BACNET_COMMUNICATION_ENABLE_DISABLE state = COMMUNICATION_ENABLE; + BACNET_CHARACTER_STRING password; + int len = 0; + int pdu_len = 0; + BACNET_ADDRESS my_address; + int bytes_sent = 0; - // decode the service request only - len = dcc_decode_service_request( - service_request, - service_len, - &timeDuration, - &state, - &password); - fprintf(stderr,"DeviceCommunicationControl!\n"); - if (len > 0) - fprintf(stderr,"DeviceCommunicationControl: " - "timeout=%u state=%u password=%s\n", - (unsigned)timeDuration, - (unsigned)state, - characterstring_value(&password)); - else - fprintf(stderr,"DeviceCommunicationControl: " - "Unable to decode request!\n"); - // prepare a reply - datalink_get_my_address(&my_address); - // encode the NPDU portion of the packet - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - src, - &my_address, - false, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); - // bad decoding or something we didn't understand - send an abort - if (len == -1) - { - pdu_len += abort_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - ABORT_REASON_OTHER); - fprintf(stderr,"DeviceCommunicationControl: " - "Sending Abort - could not decode.\n"); - } - else if (service_data->segmented_message) - { - pdu_len += abort_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); - fprintf(stderr,"DeviceCommunicationControl: " - "Sending Abort - segmented message.\n"); - } - else if (state >= MAX_BACNET_COMMUNICATION_ENABLE_DISABLE) - { - pdu_len += reject_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - REJECT_REASON_UNDEFINED_ENUMERATION); - fprintf(stderr,"DeviceCommunicationControl: " - "Sending Reject - undefined enumeration\n"); - } - else - { - if (characterstring_ansi_same(&password,My_Password)) - { - pdu_len += encode_simple_ack( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - SERVICE_CONFIRMED_DEVICE_COMMUNICATION_CONTROL); - fprintf(stderr,"DeviceCommunicationControl: " - "Sending Simple Ack!\n"); - dcc_set_status_duration(state,timeDuration); - } + // decode the service request only + len = dcc_decode_service_request(service_request, + service_len, &timeDuration, &state, &password); + fprintf(stderr, "DeviceCommunicationControl!\n"); + if (len > 0) + fprintf(stderr, "DeviceCommunicationControl: " + "timeout=%u state=%u password=%s\n", + (unsigned) timeDuration, + (unsigned) state, characterstring_value(&password)); else - { - pdu_len += bacerror_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - SERVICE_CONFIRMED_DEVICE_COMMUNICATION_CONTROL, - ERROR_CLASS_SERVICES, - ERROR_CODE_PASSWORD_FAILURE); - fprintf(stderr,"DeviceCommunicationControl: " - "Sending Error - password failure.\n"); + fprintf(stderr, "DeviceCommunicationControl: " + "Unable to decode request!\n"); + // prepare a reply + datalink_get_my_address(&my_address); + // encode the NPDU portion of the packet + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], src, &my_address, false, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); + // bad decoding or something we didn't understand - send an abort + if (len == -1) { + pdu_len += abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, ABORT_REASON_OTHER); + fprintf(stderr, "DeviceCommunicationControl: " + "Sending Abort - could not decode.\n"); + } else if (service_data->segmented_message) { + pdu_len += abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); + fprintf(stderr, "DeviceCommunicationControl: " + "Sending Abort - segmented message.\n"); + } else if (state >= MAX_BACNET_COMMUNICATION_ENABLE_DISABLE) { + pdu_len += reject_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, REJECT_REASON_UNDEFINED_ENUMERATION); + fprintf(stderr, "DeviceCommunicationControl: " + "Sending Reject - undefined enumeration\n"); + } else { + if (characterstring_ansi_same(&password, My_Password)) { + pdu_len += encode_simple_ack(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + SERVICE_CONFIRMED_DEVICE_COMMUNICATION_CONTROL); + fprintf(stderr, "DeviceCommunicationControl: " + "Sending Simple Ack!\n"); + dcc_set_status_duration(state, timeDuration); + } else { + pdu_len += + bacerror_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + SERVICE_CONFIRMED_DEVICE_COMMUNICATION_CONTROL, + ERROR_CLASS_SERVICES, ERROR_CODE_PASSWORD_FAILURE); + fprintf(stderr, + "DeviceCommunicationControl: " + "Sending Error - password failure.\n"); + } } - } - bytes_sent = datalink_send_pdu( - src, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"DeviceCommunicationControl: " - "Failed to send PDU (%s)!\n", - strerror(errno)); + bytes_sent = datalink_send_pdu(src, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, "DeviceCommunicationControl: " + "Failed to send PDU (%s)!\n", strerror(errno)); - return; + return; } diff --git a/bacnet-stack/demo/handler/h_iam.c b/bacnet-stack/demo/handler/h_iam.c index a002aeb1..91ed48a5 100644 --- a/bacnet-stack/demo/handler/h_iam.c +++ b/bacnet-stack/demo/handler/h_iam.c @@ -32,61 +32,42 @@ #include "iam.h" #include "address.h" -void handler_i_am_add( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src) +void handler_i_am_add(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src) { - int len = 0; - uint32_t device_id = 0; - unsigned max_apdu = 0; - int segmentation = 0; - uint16_t vendor_id = 0; + int len = 0; + uint32_t device_id = 0; + unsigned max_apdu = 0; + int segmentation = 0; + uint16_t vendor_id = 0; - (void)service_len; - len = iam_decode_service_request( - service_request, - &device_id, - &max_apdu, - &segmentation, - &vendor_id); - fprintf(stderr,"Received I-Am Request"); - if (len != -1) - { - fprintf(stderr," from %u!\n",device_id); - address_add(device_id, - max_apdu, - src); - } - else - fprintf(stderr,"!\n"); + (void) service_len; + len = iam_decode_service_request(service_request, + &device_id, &max_apdu, &segmentation, &vendor_id); + fprintf(stderr, "Received I-Am Request"); + if (len != -1) { + fprintf(stderr, " from %u!\n", device_id); + address_add(device_id, max_apdu, src); + } else + fprintf(stderr, "!\n"); - return; + return; } -void handler_i_am_bind( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src) +void handler_i_am_bind(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src) { - int len = 0; - uint32_t device_id = 0; - unsigned max_apdu = 0; - int segmentation = 0; - uint16_t vendor_id = 0; + int len = 0; + uint32_t device_id = 0; + unsigned max_apdu = 0; + int segmentation = 0; + uint16_t vendor_id = 0; - (void)service_len; - len = iam_decode_service_request( - service_request, - &device_id, - &max_apdu, - &segmentation, - &vendor_id); - // only add address if requested to bind - address_add_binding(device_id, - max_apdu, - src); + (void) service_len; + len = iam_decode_service_request(service_request, + &device_id, &max_apdu, &segmentation, &vendor_id); + // only add address if requested to bind + address_add_binding(device_id, max_apdu, src); - return; + return; } - diff --git a/bacnet-stack/demo/handler/h_ihave.c b/bacnet-stack/demo/handler/h_ihave.c index f5dec8ed..9a97ecc0 100644 --- a/bacnet-stack/demo/handler/h_ihave.c +++ b/bacnet-stack/demo/handler/h_ihave.c @@ -32,31 +32,24 @@ #include "bactext.h" #include "ihave.h" -void handler_i_have( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src) +void handler_i_have(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src) { - int len = 0; - BACNET_I_HAVE_DATA data; + int len = 0; + BACNET_I_HAVE_DATA data; - (void)service_len; - (void)src; - len = ihave_decode_service_request( - service_request, - service_len, - &data); - if (len != -1) - { - fprintf(stderr,"I-Have: %s %d from %s %u!\r\n", - bactext_object_type_name(data.object_id.type), - data.object_id.instance, - bactext_object_type_name(data.device_id.type), - data.device_id.instance); - } - else - fprintf(stderr,"I-Have: received, but unable to decode!\n"); + (void) service_len; + (void) src; + len = ihave_decode_service_request(service_request, + service_len, &data); + if (len != -1) { + fprintf(stderr, "I-Have: %s %d from %s %u!\r\n", + bactext_object_type_name(data.object_id.type), + data.object_id.instance, + bactext_object_type_name(data.device_id.type), + data.device_id.instance); + } else + fprintf(stderr, "I-Have: received, but unable to decode!\n"); - return; + return; } - diff --git a/bacnet-stack/demo/handler/h_rd.c b/bacnet-stack/demo/handler/h_rd.c index 24866e4e..dba93741 100644 --- a/bacnet-stack/demo/handler/h_rd.c +++ b/bacnet-stack/demo/handler/h_rd.c @@ -40,99 +40,74 @@ static BACNET_CHARACTER_STRING My_Password; -void handler_reinitialize_device( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_DATA *service_data) +void handler_reinitialize_device(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, BACNET_CONFIRMED_SERVICE_DATA * service_data) { - BACNET_REINITIALIZED_STATE state; - BACNET_CHARACTER_STRING password; - int len = 0; - int pdu_len = 0; - BACNET_ADDRESS my_address; - int bytes_sent = 0; + BACNET_REINITIALIZED_STATE state; + BACNET_CHARACTER_STRING password; + int len = 0; + int pdu_len = 0; + BACNET_ADDRESS my_address; + int bytes_sent = 0; - // decode the service request only - len = rd_decode_service_request( - service_request, - service_len, - &state, - &password); - fprintf(stderr,"ReinitializeDevice!\n"); - if (len > 0) - fprintf(stderr,"ReinitializeDevice: state=%u password=%s\n", - (unsigned)state, - characterstring_value(&password)); - else - fprintf(stderr,"ReinitializeDevice: Unable to decode request!\n"); - // prepare a reply - datalink_get_my_address(&my_address); - // encode the NPDU portion of the packet - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - src, - &my_address, - false, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); - // bad decoding or something we didn't understand - send an abort - if (len == -1) - { - pdu_len += abort_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - ABORT_REASON_OTHER); - fprintf(stderr,"ReinitializeDevice: Sending Abort - could not decode.\n"); - } - else if (service_data->segmented_message) - { - pdu_len += abort_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); - fprintf(stderr,"ReinitializeDevice: Sending Abort - segmented message.\n"); - } - else if (state >= MAX_BACNET_REINITIALIZED_STATE) - { - pdu_len += reject_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - REJECT_REASON_UNDEFINED_ENUMERATION); - fprintf(stderr,"ReinitializeDevice: Sending Reject - undefined enumeration\n"); - } - else - { - characterstring_init_ansi(&My_Password,"Jesus"); - if (characterstring_same(&password,&My_Password)) - { - pdu_len += encode_simple_ack( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - SERVICE_CONFIRMED_REINITIALIZE_DEVICE); - fprintf(stderr,"ReinitializeDevice: Sending Simple Ack!\n"); - /* FIXME: now you can reboot, restart, quit, or something clever */ - /* Note: you can use a mix of state and password to do specific stuff */ - /* Note: if you don't do something clever like actually restart, - you probably should clear any DCC status and timeouts */ - } + // decode the service request only + len = rd_decode_service_request(service_request, + service_len, &state, &password); + fprintf(stderr, "ReinitializeDevice!\n"); + if (len > 0) + fprintf(stderr, "ReinitializeDevice: state=%u password=%s\n", + (unsigned) state, characterstring_value(&password)); else - { - pdu_len += bacerror_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - SERVICE_CONFIRMED_REINITIALIZE_DEVICE, - ERROR_CLASS_SERVICES, - ERROR_CODE_PASSWORD_FAILURE); - fprintf(stderr,"ReinitializeDevice: Sending Error - password failure.\n"); + fprintf(stderr, "ReinitializeDevice: Unable to decode request!\n"); + // prepare a reply + datalink_get_my_address(&my_address); + // encode the NPDU portion of the packet + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], src, &my_address, false, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); + // bad decoding or something we didn't understand - send an abort + if (len == -1) { + pdu_len += abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, ABORT_REASON_OTHER); + fprintf(stderr, + "ReinitializeDevice: Sending Abort - could not decode.\n"); + } else if (service_data->segmented_message) { + pdu_len += abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); + fprintf(stderr, + "ReinitializeDevice: Sending Abort - segmented message.\n"); + } else if (state >= MAX_BACNET_REINITIALIZED_STATE) { + pdu_len += reject_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, REJECT_REASON_UNDEFINED_ENUMERATION); + fprintf(stderr, + "ReinitializeDevice: Sending Reject - undefined enumeration\n"); + } else { + characterstring_init_ansi(&My_Password, "Jesus"); + if (characterstring_same(&password, &My_Password)) { + pdu_len += encode_simple_ack(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + SERVICE_CONFIRMED_REINITIALIZE_DEVICE); + fprintf(stderr, "ReinitializeDevice: Sending Simple Ack!\n"); + /* FIXME: now you can reboot, restart, quit, or something clever */ + /* Note: you can use a mix of state and password to do specific stuff */ + /* Note: if you don't do something clever like actually restart, + you probably should clear any DCC status and timeouts */ + } else { + pdu_len += + bacerror_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + SERVICE_CONFIRMED_REINITIALIZE_DEVICE, + ERROR_CLASS_SERVICES, ERROR_CODE_PASSWORD_FAILURE); + fprintf(stderr, + "ReinitializeDevice: Sending Error - password failure.\n"); + } } - } - bytes_sent = datalink_send_pdu( - src, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"ReinitializeDevice: Failed to send PDU (%s)!\n", - strerror(errno)); + bytes_sent = datalink_send_pdu(src, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, "ReinitializeDevice: Failed to send PDU (%s)!\n", + strerror(errno)); - return; + return; } diff --git a/bacnet-stack/demo/handler/h_rp.c b/bacnet-stack/demo/handler/h_rp.c index a8027332..99bb92a1 100644 --- a/bacnet-stack/demo/handler/h_rp.c +++ b/bacnet-stack/demo/handler/h_rp.c @@ -43,206 +43,148 @@ #include "bacfile.h" #endif -static uint8_t Temp_Buf[MAX_APDU] = {0}; +static uint8_t Temp_Buf[MAX_APDU] = { 0 }; -void handler_read_property( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_DATA *service_data) +void handler_read_property(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, BACNET_CONFIRMED_SERVICE_DATA * service_data) { - BACNET_READ_PROPERTY_DATA data; - int len = 0; - int pdu_len = 0; - BACNET_ADDRESS my_address; - bool send = false; - bool error = false; - int bytes_sent = 0; - BACNET_ERROR_CLASS error_class = ERROR_CLASS_OBJECT; - BACNET_ERROR_CODE error_code = ERROR_CODE_UNKNOWN_OBJECT; + BACNET_READ_PROPERTY_DATA data; + int len = 0; + int pdu_len = 0; + BACNET_ADDRESS my_address; + bool send = false; + bool error = false; + int bytes_sent = 0; + BACNET_ERROR_CLASS error_class = ERROR_CLASS_OBJECT; + BACNET_ERROR_CODE error_code = ERROR_CODE_UNKNOWN_OBJECT; - len = rp_decode_service_request( - service_request, - service_len, - &data); - if (len <= 0) - fprintf(stderr,"Unable to decode Read-Property Request!\n"); - // prepare a reply - datalink_get_my_address(&my_address); - // encode the NPDU portion of the packet - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - src, - &my_address, - false, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); - // bad decoding - send an abort - if (len == -1) - { - pdu_len += abort_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - ABORT_REASON_OTHER); - fprintf(stderr,"Sending Abort!\n"); - send = true; - } - else if (service_data->segmented_message) - { - pdu_len += abort_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); - fprintf(stderr,"Sending Abort!\n"); - send = true; - } - else - { - switch (data.object_type) - { - case OBJECT_DEVICE: - // FIXME: probably need a length limitation sent with encode - if (data.object_instance == Device_Object_Instance_Number()) - { - len = Device_Encode_Property_APDU( - &Temp_Buf[0], - data.object_property, - data.array_index, - &error_class, - &error_code); - if (len >= 0) - { - // encode the APDU portion of the packet - data.application_data = &Temp_Buf[0]; - data.application_data_len = len; + len = rp_decode_service_request(service_request, service_len, &data); + if (len <= 0) + fprintf(stderr, "Unable to decode Read-Property Request!\n"); + // prepare a reply + datalink_get_my_address(&my_address); + // encode the NPDU portion of the packet + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], src, &my_address, false, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); + // bad decoding - send an abort + if (len == -1) { + pdu_len += abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, ABORT_REASON_OTHER); + fprintf(stderr, "Sending Abort!\n"); + send = true; + } else if (service_data->segmented_message) { + pdu_len += abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); + fprintf(stderr, "Sending Abort!\n"); + send = true; + } else { + switch (data.object_type) { + case OBJECT_DEVICE: // FIXME: probably need a length limitation sent with encode - pdu_len += rp_ack_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - &data); - fprintf(stderr,"Sending Read Property Ack!\n"); - send = true; - } - else + if (data.object_instance == Device_Object_Instance_Number()) { + len = Device_Encode_Property_APDU(&Temp_Buf[0], + data.object_property, + data.array_index, &error_class, &error_code); + if (len >= 0) { + // encode the APDU portion of the packet + data.application_data = &Temp_Buf[0]; + data.application_data_len = len; + // FIXME: probably need a length limitation sent with encode + pdu_len += + rp_ack_encode_apdu(&Handler_Transmit_Buffer + [pdu_len], service_data->invoke_id, &data); + fprintf(stderr, "Sending Read Property Ack!\n"); + send = true; + } else + error = true; + } else + error = true; + break; + case OBJECT_ANALOG_INPUT: + if (Analog_Input_Valid_Instance(data.object_instance)) { + len = Analog_Input_Encode_Property_APDU(&Temp_Buf[0], + data.object_instance, + data.object_property, + data.array_index, &error_class, &error_code); + if (len >= 0) { + // encode the APDU portion of the packet + data.application_data = &Temp_Buf[0]; + data.application_data_len = len; + // FIXME: probably need a length limitation sent with encode + pdu_len += + rp_ack_encode_apdu(&Handler_Transmit_Buffer + [pdu_len], service_data->invoke_id, &data); + fprintf(stderr, "Sending Read Property Ack!\n"); + send = true; + } else + error = true; + } else + error = true; + break; + case OBJECT_ANALOG_OUTPUT: + if (Analog_Output_Valid_Instance(data.object_instance)) { + len = Analog_Output_Encode_Property_APDU(&Temp_Buf[0], + data.object_instance, + data.object_property, + data.array_index, &error_class, &error_code); + if (len >= 0) { + // encode the APDU portion of the packet + data.application_data = &Temp_Buf[0]; + data.application_data_len = len; + // FIXME: probably need a length limitation sent with encode + pdu_len += + rp_ack_encode_apdu(&Handler_Transmit_Buffer + [pdu_len], service_data->invoke_id, &data); + fprintf(stderr, "Sending Read Property Ack!\n"); + send = true; + } else + error = true; + } else + error = true; + break; +#if BACFILE + case OBJECT_FILE: + if (bacfile_valid_instance(data.object_instance)) { + len = bacfile_encode_property_apdu(&Temp_Buf[0], + data.object_instance, + data.object_property, + data.array_index, &error_class, &error_code); + if (len >= 0) { + // encode the APDU portion of the packet + data.application_data = &Temp_Buf[0]; + data.application_data_len = len; + // FIXME: probably need a length limitation sent with encode + pdu_len += + rp_ack_encode_apdu(&Handler_Transmit_Buffer + [pdu_len], service_data->invoke_id, &data); + fprintf(stderr, "Sending Read Property Ack!\n"); + send = true; + } else + error = true; + } else + error = true; + break; +#endif + default: error = true; + break; } - else - error = true; - break; - case OBJECT_ANALOG_INPUT: - if (Analog_Input_Valid_Instance(data.object_instance)) - { - len = Analog_Input_Encode_Property_APDU( - &Temp_Buf[0], - data.object_instance, - data.object_property, - data.array_index, - &error_class, - &error_code); - if (len >= 0) - { - // encode the APDU portion of the packet - data.application_data = &Temp_Buf[0]; - data.application_data_len = len; - // FIXME: probably need a length limitation sent with encode - pdu_len += rp_ack_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - &data); - fprintf(stderr,"Sending Read Property Ack!\n"); - send = true; - } - else - error = true; - } - else - error = true; - break; - case OBJECT_ANALOG_OUTPUT: - if (Analog_Output_Valid_Instance(data.object_instance)) - { - len = Analog_Output_Encode_Property_APDU( - &Temp_Buf[0], - data.object_instance, - data.object_property, - data.array_index, - &error_class, - &error_code); - if (len >= 0) - { - // encode the APDU portion of the packet - data.application_data = &Temp_Buf[0]; - data.application_data_len = len; - // FIXME: probably need a length limitation sent with encode - pdu_len += rp_ack_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - &data); - fprintf(stderr,"Sending Read Property Ack!\n"); - send = true; - } - else - error = true; - } - else - error = true; - break; - #if BACFILE - case OBJECT_FILE: - if (bacfile_valid_instance(data.object_instance)) - { - len = bacfile_encode_property_apdu( - &Temp_Buf[0], - data.object_instance, - data.object_property, - data.array_index, - &error_class, - &error_code); - if (len >= 0) - { - // encode the APDU portion of the packet - data.application_data = &Temp_Buf[0]; - data.application_data_len = len; - // FIXME: probably need a length limitation sent with encode - pdu_len += rp_ack_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - &data); - fprintf(stderr,"Sending Read Property Ack!\n"); - send = true; - } - else - error = true; - } - else - error = true; - break; - #endif - default: - error = true; - break; } - } - if (error) - { - pdu_len += bacerror_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - SERVICE_CONFIRMED_READ_PROPERTY, - error_class, - error_code); - fprintf(stderr,"Sending Read Property Error!\n"); - send = true; - } - if (send) - { - bytes_sent = datalink_send_pdu( - src, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to send PDU (%s)!\n", strerror(errno)); - } + if (error) { + pdu_len += bacerror_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + SERVICE_CONFIRMED_READ_PROPERTY, error_class, error_code); + fprintf(stderr, "Sending Read Property Error!\n"); + send = true; + } + if (send) { + bytes_sent = datalink_send_pdu(src, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, "Failed to send PDU (%s)!\n", strerror(errno)); + } - return; + return; } - diff --git a/bacnet-stack/demo/handler/h_rp_a.c b/bacnet-stack/demo/handler/h_rp_a.c index b0d23530..d77ebac8 100644 --- a/bacnet-stack/demo/handler/h_rp_a.c +++ b/bacnet-stack/demo/handler/h_rp_a.c @@ -42,85 +42,72 @@ #include "txbuf.h" /* for debugging... */ -static void PrintReadPropertyData(BACNET_READ_PROPERTY_DATA *data) +static void PrintReadPropertyData(BACNET_READ_PROPERTY_DATA * data) { - BACNET_APPLICATION_DATA_VALUE value; /* for decode value data */ - int len = 0; - uint8_t *application_data; - int application_data_len; - bool first_value = true; - bool print_brace = false; + BACNET_APPLICATION_DATA_VALUE value; /* for decode value data */ + int len = 0; + uint8_t *application_data; + int application_data_len; + bool first_value = true; + bool print_brace = false; - if (data) - { - #if 0 - if (data->array_index == BACNET_ARRAY_ALL) - fprintf(stderr,"%s #%u %s\n", - bactext_object_type_name(data->object_type), - data->object_instance, - bactext_property_name(data->object_property)); - else - fprintf(stderr,"%s #%u %s[%d]\n", - bactext_object_type_name(data->object_type), - data->object_instance, - bactext_property_name(data->object_property), - data->array_index); - #endif - application_data = data->application_data; - application_data_len = data->application_data_len; - /* value? need to loop until all of the len is gone... */ - for (;;) - { - len = bacapp_decode_application_data( - application_data, - application_data_len, - &value); - if (first_value && (len < application_data_len)) - { - first_value = false; - fprintf(stdout,"{"); - print_brace = true; - } - bacapp_print_value(stdout,&value,data->object_property); - if (len) - { - if (len < application_data_len) - { - application_data += len; - application_data_len -= len; - /* there's more! */ - fprintf(stdout,","); - } + if (data) { +#if 0 + if (data->array_index == BACNET_ARRAY_ALL) + fprintf(stderr, "%s #%u %s\n", + bactext_object_type_name(data->object_type), + data->object_instance, + bactext_property_name(data->object_property)); else - break; - } - else - break; + fprintf(stderr, "%s #%u %s[%d]\n", + bactext_object_type_name(data->object_type), + data->object_instance, + bactext_property_name(data->object_property), + data->array_index); +#endif + application_data = data->application_data; + application_data_len = data->application_data_len; + /* value? need to loop until all of the len is gone... */ + for (;;) { + len = bacapp_decode_application_data(application_data, + application_data_len, &value); + if (first_value && (len < application_data_len)) { + first_value = false; + fprintf(stdout, "{"); + print_brace = true; + } + bacapp_print_value(stdout, &value, data->object_property); + if (len) { + if (len < application_data_len) { + application_data += len; + application_data_len -= len; + /* there's more! */ + fprintf(stdout, ","); + } else + break; + } else + break; + } + if (print_brace) + fprintf(stdout, "}"); + fprintf(stdout, "\r\n"); } - if (print_brace) - fprintf(stdout,"}"); - fprintf(stdout,"\r\n"); - } } -void handler_read_property_ack( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_ACK_DATA *service_data) +void handler_read_property_ack(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, BACNET_CONFIRMED_SERVICE_ACK_DATA * service_data) { - int len = 0; - BACNET_READ_PROPERTY_DATA data; + int len = 0; + BACNET_READ_PROPERTY_DATA data; - (void)src; - (void)service_data; /* we could use these... */ - len = rp_ack_decode_service_request( - service_request, - service_len, - &data); - #if 0 - fprintf(stderr,"Received Read-Property Ack!\n"); - #endif - if (len > 0) - PrintReadPropertyData(&data); + (void) src; + (void) service_data; /* we could use these... */ + len = rp_ack_decode_service_request(service_request, + service_len, &data); +#if 0 + fprintf(stderr, "Received Read-Property Ack!\n"); +#endif + if (len > 0) + PrintReadPropertyData(&data); } diff --git a/bacnet-stack/demo/handler/h_whohas.c b/bacnet-stack/demo/handler/h_whohas.c index 44eb526a..0352aa0c 100644 --- a/bacnet-stack/demo/handler/h_whohas.c +++ b/bacnet-stack/demo/handler/h_whohas.c @@ -35,65 +35,51 @@ #include "device.h" #include "client.h" -void handler_who_has( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src) +void handler_who_has(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src) { - int len = 0; - BACNET_WHO_HAS_DATA data; - bool directed_to_me = false; - int object_type = 0; - uint32_t object_instance = 0; - char *object_name = NULL; - bool found = false; + int len = 0; + BACNET_WHO_HAS_DATA data; + bool directed_to_me = false; + int object_type = 0; + uint32_t object_instance = 0; + char *object_name = NULL; + bool found = false; - (void)src; - len = whohas_decode_service_request( - service_request, - service_len, - &data); - if (len > 0) - { - if ((data.low_limit == -1) || (data.high_limit == -1)) - directed_to_me = true; - else if ((Device_Object_Instance_Number() >= (uint32_t)data.low_limit) && - (Device_Object_Instance_Number() <= (uint32_t)data.high_limit)) - directed_to_me = true; - if (directed_to_me) - { - /* do we have such an object? If so, send an I-Have. - note: we should have only 1 of such an object */ - if (data.object_name) - { - /* valid name in my device? */ - object_name = characterstring_value(&data.object.name); - found = Device_Valid_Object_Name( - object_name, - &object_type, - &object_instance); - if (found) - Send_I_Have( - Device_Object_Instance_Number(), - object_type, - object_instance, - object_name); - } - else - { - /* valid object in my device? */ - object_name = Device_Valid_Object_Id( - data.object.identifier.type, - data.object.identifier.instance); - if (object_name) - Send_I_Have( - Device_Object_Instance_Number(), - data.object.identifier.type, - data.object.identifier.instance, - object_name); - } + (void) src; + len = whohas_decode_service_request(service_request, + service_len, &data); + if (len > 0) { + if ((data.low_limit == -1) || (data.high_limit == -1)) + directed_to_me = true; + else if ((Device_Object_Instance_Number() >= + (uint32_t) data.low_limit) + && (Device_Object_Instance_Number() <= + (uint32_t) data.high_limit)) + directed_to_me = true; + if (directed_to_me) { + /* do we have such an object? If so, send an I-Have. + note: we should have only 1 of such an object */ + if (data.object_name) { + /* valid name in my device? */ + object_name = characterstring_value(&data.object.name); + found = Device_Valid_Object_Name(object_name, + &object_type, &object_instance); + if (found) + Send_I_Have(Device_Object_Instance_Number(), + object_type, object_instance, object_name); + } else { + /* valid object in my device? */ + object_name = + Device_Valid_Object_Id(data.object.identifier.type, + data.object.identifier.instance); + if (object_name) + Send_I_Have(Device_Object_Instance_Number(), + data.object.identifier.type, + data.object.identifier.instance, object_name); + } + } } - } - return; + return; } diff --git a/bacnet-stack/demo/handler/h_whois.c b/bacnet-stack/demo/handler/h_whois.c index 02357d18..c661fcfb 100644 --- a/bacnet-stack/demo/handler/h_whois.c +++ b/bacnet-stack/demo/handler/h_whois.c @@ -37,31 +37,25 @@ /* global flag to send an I-Am */ bool I_Am_Request = true; -void handler_who_is( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src) +void handler_who_is(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src) { - int len = 0; - int32_t low_limit = 0; - int32_t high_limit = 0; + int len = 0; + int32_t low_limit = 0; + int32_t high_limit = 0; - (void)src; - len = whois_decode_service_request( - service_request, - service_len, - &low_limit, - &high_limit); - /* in our simple system, we just set a flag and let the main loop - send the I-Am request. */ - if (len == 0) - I_Am_Request = true; - else if (len != -1) - { - if ((Device_Object_Instance_Number() >= (uint32_t)low_limit) && - (Device_Object_Instance_Number() <= (uint32_t)high_limit)) - I_Am_Request = true; - } + (void) src; + len = whois_decode_service_request(service_request, + service_len, &low_limit, &high_limit); + /* in our simple system, we just set a flag and let the main loop + send the I-Am request. */ + if (len == 0) + I_Am_Request = true; + else if (len != -1) { + if ((Device_Object_Instance_Number() >= (uint32_t) low_limit) && + (Device_Object_Instance_Number() <= (uint32_t) high_limit)) + I_Am_Request = true; + } - return; + return; } diff --git a/bacnet-stack/demo/handler/h_wp.c b/bacnet-stack/demo/handler/h_wp.c index e04c0601..8cdaa91a 100644 --- a/bacnet-stack/demo/handler/h_wp.c +++ b/bacnet-stack/demo/handler/h_wp.c @@ -43,132 +43,101 @@ #include "bacfile.h" #endif -void handler_write_property( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_DATA *service_data) +void handler_write_property(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, BACNET_CONFIRMED_SERVICE_DATA * service_data) { - BACNET_WRITE_PROPERTY_DATA wp_data; - int len = 0; - int pdu_len = 0; - BACNET_ADDRESS my_address; - BACNET_ERROR_CLASS error_class = ERROR_CLASS_OBJECT; - BACNET_ERROR_CODE error_code = ERROR_CODE_UNKNOWN_OBJECT; - int bytes_sent = 0; + BACNET_WRITE_PROPERTY_DATA wp_data; + int len = 0; + int pdu_len = 0; + BACNET_ADDRESS my_address; + BACNET_ERROR_CLASS error_class = ERROR_CLASS_OBJECT; + BACNET_ERROR_CODE error_code = ERROR_CODE_UNKNOWN_OBJECT; + int bytes_sent = 0; - // decode the service request only - len = wp_decode_service_request( - service_request, - service_len, - &wp_data); - fprintf(stderr,"Received Write-Property Request!\n"); - if (len > 0) - fprintf(stderr,"type=%u instance=%u property=%u index=%d\n", - wp_data.object_type, - wp_data.object_instance, - wp_data.object_property, - wp_data.array_index); - else - fprintf(stderr,"Unable to decode Write-Property Request!\n"); - // prepare a reply - datalink_get_my_address(&my_address); - // encode the NPDU portion of the packet - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - src, - &my_address, - false, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); - // bad decoding or something we didn't understand - send an abort - if (len == -1) - { - pdu_len += abort_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - ABORT_REASON_OTHER); - fprintf(stderr,"Sending Abort!\n"); - } - else if (service_data->segmented_message) - { - pdu_len += abort_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); - fprintf(stderr,"Sending Abort!\n"); - } - else - { - switch (wp_data.object_type) - { - case OBJECT_DEVICE: - if (Device_Write_Property(&wp_data,&error_class,&error_code)) - { - pdu_len += encode_simple_ack( - &Handler_Transmit_Buffer[pdu_len], + // decode the service request only + len = wp_decode_service_request(service_request, + service_len, &wp_data); + fprintf(stderr, "Received Write-Property Request!\n"); + if (len > 0) + fprintf(stderr, "type=%u instance=%u property=%u index=%d\n", + wp_data.object_type, + wp_data.object_instance, + wp_data.object_property, wp_data.array_index); + else + fprintf(stderr, "Unable to decode Write-Property Request!\n"); + // prepare a reply + datalink_get_my_address(&my_address); + // encode the NPDU portion of the packet + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], src, &my_address, false, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); + // bad decoding or something we didn't understand - send an abort + if (len == -1) { + pdu_len += abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, ABORT_REASON_OTHER); + fprintf(stderr, "Sending Abort!\n"); + } else if (service_data->segmented_message) { + pdu_len += abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], service_data->invoke_id, - SERVICE_CONFIRMED_WRITE_PROPERTY); - fprintf(stderr,"Sending Write Property Simple Ack!\n"); + ABORT_REASON_SEGMENTATION_NOT_SUPPORTED); + fprintf(stderr, "Sending Abort!\n"); + } else { + switch (wp_data.object_type) { + case OBJECT_DEVICE: + if (Device_Write_Property(&wp_data, &error_class, &error_code)) { + pdu_len += + encode_simple_ack(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + SERVICE_CONFIRMED_WRITE_PROPERTY); + fprintf(stderr, "Sending Write Property Simple Ack!\n"); + } else { + pdu_len += + bacerror_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + SERVICE_CONFIRMED_WRITE_PROPERTY, error_class, + error_code); + fprintf(stderr, "Sending Write Property Error!\n"); + } + break; + case OBJECT_ANALOG_INPUT: + error_class = ERROR_CLASS_PROPERTY; + error_code = ERROR_CODE_WRITE_ACCESS_DENIED; + pdu_len += + bacerror_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, SERVICE_CONFIRMED_WRITE_PROPERTY, + error_class, error_code); + fprintf(stderr, "Sending Write Access Error!\n"); + break; + case OBJECT_ANALOG_OUTPUT: + if (Analog_Output_Write_Property(&wp_data, &error_class, + &error_code)) { + pdu_len += + encode_simple_ack(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + SERVICE_CONFIRMED_WRITE_PROPERTY); + fprintf(stderr, "Sending Write Property Simple Ack!\n"); + } else { + pdu_len += + bacerror_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, + SERVICE_CONFIRMED_WRITE_PROPERTY, error_class, + error_code); + fprintf(stderr, "Sending Write Access Error!\n"); + } + break; + default: + pdu_len += + bacerror_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, SERVICE_CONFIRMED_WRITE_PROPERTY, + error_class, error_code); + fprintf(stderr, "Sending Unknown Object Error!\n"); + break; } - else - { - pdu_len += bacerror_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - SERVICE_CONFIRMED_WRITE_PROPERTY, - error_class, - error_code); - fprintf(stderr,"Sending Write Property Error!\n"); - } - break; - case OBJECT_ANALOG_INPUT: - error_class = ERROR_CLASS_PROPERTY; - error_code = ERROR_CODE_WRITE_ACCESS_DENIED; - pdu_len += bacerror_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - SERVICE_CONFIRMED_WRITE_PROPERTY, - error_class, - error_code); - fprintf(stderr,"Sending Write Access Error!\n"); - break; - case OBJECT_ANALOG_OUTPUT: - if (Analog_Output_Write_Property(&wp_data,&error_class,&error_code)) - { - pdu_len += encode_simple_ack( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - SERVICE_CONFIRMED_WRITE_PROPERTY); - fprintf(stderr,"Sending Write Property Simple Ack!\n"); - } - else - { - pdu_len += bacerror_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - SERVICE_CONFIRMED_WRITE_PROPERTY, - error_class, - error_code); - fprintf(stderr,"Sending Write Access Error!\n"); - } - break; - default: - pdu_len += bacerror_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - SERVICE_CONFIRMED_WRITE_PROPERTY, - error_class, - error_code); - fprintf(stderr,"Sending Unknown Object Error!\n"); - break; } - } - bytes_sent = datalink_send_pdu( - src, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to send PDU (%s)!\n", strerror(errno)); + bytes_sent = datalink_send_pdu(src, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, "Failed to send PDU (%s)!\n", strerror(errno)); - return; + return; } diff --git a/bacnet-stack/demo/handler/handlers.h b/bacnet-stack/demo/handler/handlers.h index be920eab..e937e01f 100644 --- a/bacnet-stack/demo/handler/handlers.h +++ b/bacnet-stack/demo/handler/handlers.h @@ -37,83 +37,64 @@ extern bool I_Am_Request; #ifdef __cplusplus extern "C" { -#endif /* __cplusplus */ +#endif /* __cplusplus */ -void handler_unrecognized_service( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *dest, - BACNET_CONFIRMED_SERVICE_DATA *service_data); + void handler_unrecognized_service(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * dest, + BACNET_CONFIRMED_SERVICE_DATA * service_data); -void handler_who_is( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src); - -void handler_who_has( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src); + void handler_who_is(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src); -void handler_i_am_add( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src); - -void handler_i_am_bind( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src); - -void handler_read_property( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_DATA *service_data); + void handler_who_has(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src); -void handler_read_property_ack( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_ACK_DATA *service_data); + void handler_i_am_add(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src); -void handler_write_property( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_DATA *service_data); + void handler_i_am_bind(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src); -void handler_atomic_read_file( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_DATA *service_data); + void handler_read_property(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, + BACNET_CONFIRMED_SERVICE_DATA * service_data); -void handler_atomic_read_file_ack( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_ACK_DATA *service_data); + void handler_read_property_ack(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, + BACNET_CONFIRMED_SERVICE_ACK_DATA * service_data); -void handler_reinitialize_device( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_DATA *service_data); + void handler_write_property(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, + BACNET_CONFIRMED_SERVICE_DATA * service_data); -void handler_device_communication_control( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_DATA *service_data); + void handler_atomic_read_file(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, + BACNET_CONFIRMED_SERVICE_DATA * service_data); -void handler_i_have( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src); + void handler_atomic_read_file_ack(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, + BACNET_CONFIRMED_SERVICE_ACK_DATA * service_data); + + void handler_reinitialize_device(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, + BACNET_CONFIRMED_SERVICE_DATA * service_data); + + void handler_device_communication_control(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, + BACNET_CONFIRMED_SERVICE_DATA * service_data); + + void handler_i_have(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src); #ifdef __cplusplus } -#endif /* __cplusplus */ - +#endif /* __cplusplus */ #endif diff --git a/bacnet-stack/demo/handler/noserv.c b/bacnet-stack/demo/handler/noserv.c index 2fdc8427..84fb7d49 100644 --- a/bacnet-stack/demo/handler/noserv.c +++ b/bacnet-stack/demo/handler/noserv.c @@ -34,40 +34,30 @@ #include "npdu.h" #include "reject.h" -void handler_unrecognized_service( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *dest, - BACNET_CONFIRMED_SERVICE_DATA *service_data) +void handler_unrecognized_service(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * dest, BACNET_CONFIRMED_SERVICE_DATA * service_data) { - BACNET_ADDRESS src; - int pdu_len = 0; - int bytes_sent = 0; - - (void)service_request; - (void)service_len; - datalink_get_my_address(&src); + BACNET_ADDRESS src; + int pdu_len = 0; + int bytes_sent = 0; - // encode the NPDU portion of the packet - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - dest, - &src, - false, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); - - // encode the APDU portion of the packet - pdu_len += reject_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - service_data->invoke_id, - REJECT_REASON_UNRECOGNIZED_SERVICE); + (void) service_request; + (void) service_len; + datalink_get_my_address(&src); - bytes_sent = datalink_send_pdu( - dest, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent > 0) - fprintf(stderr,"Sent Reject!\n"); - else - fprintf(stderr,"Failed to Send Reject (%s)!\n", strerror(errno)); + // encode the NPDU portion of the packet + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], dest, &src, false, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); + + // encode the APDU portion of the packet + pdu_len += reject_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, REJECT_REASON_UNRECOGNIZED_SERVICE); + + bytes_sent = datalink_send_pdu(dest, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent > 0) + fprintf(stderr, "Sent Reject!\n"); + else + fprintf(stderr, "Failed to Send Reject (%s)!\n", strerror(errno)); } diff --git a/bacnet-stack/demo/handler/s_dcc.c b/bacnet-stack/demo/handler/s_dcc.c index fc357436..ba4aac5e 100644 --- a/bacnet-stack/demo/handler/s_dcc.c +++ b/bacnet-stack/demo/handler/s_dcc.c @@ -41,73 +41,56 @@ #include "handlers.h" #include "txbuf.h" -uint8_t Send_Device_Communication_Control_Request( - uint32_t device_id, - uint16_t timeDuration, /* 0=optional */ - BACNET_COMMUNICATION_ENABLE_DISABLE state, - char *password) /* NULL=optional */ -{ - BACNET_ADDRESS dest; - BACNET_ADDRESS my_address; - unsigned max_apdu = 0; - uint8_t invoke_id = 0; - bool status = false; - int pdu_len = 0; - int bytes_sent = 0; - BACNET_CHARACTER_STRING password_string; +uint8_t Send_Device_Communication_Control_Request(uint32_t device_id, uint16_t timeDuration, /* 0=optional */ + BACNET_COMMUNICATION_ENABLE_DISABLE state, char *password) +{ /* NULL=optional */ + BACNET_ADDRESS dest; + BACNET_ADDRESS my_address; + unsigned max_apdu = 0; + uint8_t invoke_id = 0; + bool status = false; + int pdu_len = 0; + int bytes_sent = 0; + BACNET_CHARACTER_STRING password_string; - if (!dcc_communication_enabled()) - return 0; + if (!dcc_communication_enabled()) + return 0; - /* is the device bound? */ - status = address_get_by_device(device_id, &max_apdu, &dest); - /* is there a tsm available? */ - if (status) - status = tsm_transaction_available(); - if (status) - { - datalink_get_my_address(&my_address); - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - &my_address, - true, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); + /* is the device bound? */ + status = address_get_by_device(device_id, &max_apdu, &dest); + /* is there a tsm available? */ + if (status) + status = tsm_transaction_available(); + if (status) { + datalink_get_my_address(&my_address); + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, &my_address, true, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); - invoke_id = tsm_next_free_invokeID(); - // load the data for the encoding - characterstring_init_ansi(&password_string,password); - pdu_len += dcc_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - invoke_id, - timeDuration, - state, - password?&password_string:NULL); - /* will it fit in the sender? - note: if there is a bottleneck router in between - us and the destination, we won't know unless - we have a way to check for that and update the - max_apdu in the address binding table. */ - if ((unsigned)pdu_len < max_apdu) - { - tsm_set_confirmed_unsegmented_transaction( - invoke_id, - &dest, - &Handler_Transmit_Buffer[0], - pdu_len); - bytes_sent = datalink_send_pdu( - &dest, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send DeviceCommunicationControl Request (%s)!\n", - strerror(errno)); + invoke_id = tsm_next_free_invokeID(); + // load the data for the encoding + characterstring_init_ansi(&password_string, password); + pdu_len += dcc_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + invoke_id, + timeDuration, state, password ? &password_string : NULL); + /* will it fit in the sender? + note: if there is a bottleneck router in between + us and the destination, we won't know unless + we have a way to check for that and update the + max_apdu in the address binding table. */ + if ((unsigned) pdu_len < max_apdu) { + tsm_set_confirmed_unsegmented_transaction(invoke_id, + &dest, &Handler_Transmit_Buffer[0], pdu_len); + bytes_sent = datalink_send_pdu(&dest, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, + "Failed to Send DeviceCommunicationControl Request (%s)!\n", + strerror(errno)); + } else + fprintf(stderr, + "Failed to Send DeviceCommunicationControl Request " + "(exceeds destination maximum APDU)!\n"); } - else - fprintf(stderr,"Failed to Send DeviceCommunicationControl Request " - "(exceeds destination maximum APDU)!\n"); - } - - return invoke_id; -} + return invoke_id; +} diff --git a/bacnet-stack/demo/handler/s_ihave.c b/bacnet-stack/demo/handler/s_ihave.c index 5b46f933..880bff72 100644 --- a/bacnet-stack/demo/handler/s_ihave.c +++ b/bacnet-stack/demo/handler/s_ihave.c @@ -43,43 +43,34 @@ #include "txbuf.h" /* find a specific device, or use -1 for limit if you want unlimited */ -void Send_I_Have( - uint32_t device_id, - BACNET_OBJECT_TYPE object_type, - uint32_t object_instance, - char *object_name) +void Send_I_Have(uint32_t device_id, + BACNET_OBJECT_TYPE object_type, + uint32_t object_instance, char *object_name) { - int pdu_len = 0; - BACNET_ADDRESS dest; - int bytes_sent = 0; - BACNET_I_HAVE_DATA data; + int pdu_len = 0; + BACNET_ADDRESS dest; + int bytes_sent = 0; + BACNET_I_HAVE_DATA data; - /* if we are forbidden to send, don't send! */ - if (!dcc_communication_enabled()) - return; - /* Who-Has is a global broadcast */ - datalink_get_broadcast_address(&dest); - /* encode the NPDU portion of the packet */ - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - NULL, - false, /* true for confirmed messages */ - MESSAGE_PRIORITY_NORMAL); - /* encode the APDU portion of the packet */ - data.device_id.type = OBJECT_DEVICE; - data.device_id.instance = device_id; - data.object_id.type = object_type; - data.object_id.instance = object_instance; - characterstring_init_ansi(&data.object_name,object_name); - pdu_len += ihave_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - &data); - /* send the data */ - bytes_sent = datalink_send_pdu( - &dest, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send I-Have Reply (%s)!\n", strerror(errno)); + /* if we are forbidden to send, don't send! */ + if (!dcc_communication_enabled()) + return; + /* Who-Has is a global broadcast */ + datalink_get_broadcast_address(&dest); + /* encode the NPDU portion of the packet */ + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, NULL, false, /* true for confirmed messages */ + MESSAGE_PRIORITY_NORMAL); + /* encode the APDU portion of the packet */ + data.device_id.type = OBJECT_DEVICE; + data.device_id.instance = device_id; + data.object_id.type = object_type; + data.object_id.instance = object_instance; + characterstring_init_ansi(&data.object_name, object_name); + pdu_len += ihave_encode_apdu(&Handler_Transmit_Buffer[pdu_len], &data); + /* send the data */ + bytes_sent = datalink_send_pdu(&dest, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, "Failed to Send I-Have Reply (%s)!\n", + strerror(errno)); } diff --git a/bacnet-stack/demo/handler/s_rd.c b/bacnet-stack/demo/handler/s_rd.c index 0f912e14..114567f1 100644 --- a/bacnet-stack/demo/handler/s_rd.c +++ b/bacnet-stack/demo/handler/s_rd.c @@ -42,71 +42,54 @@ #include "handlers.h" #include "txbuf.h" -uint8_t Send_Reinitialize_Device_Request( - uint32_t device_id, - BACNET_REINITIALIZED_STATE state, - char *password) +uint8_t Send_Reinitialize_Device_Request(uint32_t device_id, + BACNET_REINITIALIZED_STATE state, char *password) { - BACNET_ADDRESS dest; - BACNET_ADDRESS my_address; - unsigned max_apdu = 0; - uint8_t invoke_id = 0; - bool status = false; - int pdu_len = 0; - int bytes_sent = 0; - BACNET_CHARACTER_STRING password_string; + BACNET_ADDRESS dest; + BACNET_ADDRESS my_address; + unsigned max_apdu = 0; + uint8_t invoke_id = 0; + bool status = false; + int pdu_len = 0; + int bytes_sent = 0; + BACNET_CHARACTER_STRING password_string; - if (!dcc_communication_enabled()) - return 0; + if (!dcc_communication_enabled()) + return 0; - /* is the device bound? */ - status = address_get_by_device(device_id, &max_apdu, &dest); - /* is there a tsm available? */ - if (status) - status = tsm_transaction_available(); - if (status) - { - datalink_get_my_address(&my_address); - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - &my_address, - true, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); + /* is the device bound? */ + status = address_get_by_device(device_id, &max_apdu, &dest); + /* is there a tsm available? */ + if (status) + status = tsm_transaction_available(); + if (status) { + datalink_get_my_address(&my_address); + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, &my_address, true, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); - invoke_id = tsm_next_free_invokeID(); - // load the data for the encoding - characterstring_init_ansi(&password_string,password); - pdu_len += rd_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - invoke_id, - state, - password?&password_string:NULL); - /* will it fit in the sender? - note: if there is a bottleneck router in between - us and the destination, we won't know unless - we have a way to check for that and update the - max_apdu in the address binding table. */ - if ((unsigned)pdu_len < max_apdu) - { - tsm_set_confirmed_unsegmented_transaction( - invoke_id, - &dest, - &Handler_Transmit_Buffer[0], - pdu_len); - bytes_sent = datalink_send_pdu( - &dest, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send ReinitializeDevice Request (%s)!\n", - strerror(errno)); + invoke_id = tsm_next_free_invokeID(); + // load the data for the encoding + characterstring_init_ansi(&password_string, password); + pdu_len += rd_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + invoke_id, state, password ? &password_string : NULL); + /* will it fit in the sender? + note: if there is a bottleneck router in between + us and the destination, we won't know unless + we have a way to check for that and update the + max_apdu in the address binding table. */ + if ((unsigned) pdu_len < max_apdu) { + tsm_set_confirmed_unsegmented_transaction(invoke_id, + &dest, &Handler_Transmit_Buffer[0], pdu_len); + bytes_sent = datalink_send_pdu(&dest, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, + "Failed to Send ReinitializeDevice Request (%s)!\n", + strerror(errno)); + } else + fprintf(stderr, "Failed to Send ReinitializeDevice Request " + "(exceeds destination maximum APDU)!\n"); } - else - fprintf(stderr,"Failed to Send ReinitializeDevice Request " - "(exceeds destination maximum APDU)!\n"); - } - - return invoke_id; -} + return invoke_id; +} diff --git a/bacnet-stack/demo/handler/s_rp.c b/bacnet-stack/demo/handler/s_rp.c index 8ed48f3c..829e15bc 100644 --- a/bacnet-stack/demo/handler/s_rp.c +++ b/bacnet-stack/demo/handler/s_rp.c @@ -43,74 +43,59 @@ #include "txbuf.h" /* returns invoke id of 0 if device is not bound or no tsm available */ -uint8_t Send_Read_Property_Request( - uint32_t device_id, /* destination device */ - BACNET_OBJECT_TYPE object_type, - uint32_t object_instance, - BACNET_PROPERTY_ID object_property, - int32_t array_index) +uint8_t Send_Read_Property_Request(uint32_t device_id, /* destination device */ + BACNET_OBJECT_TYPE object_type, + uint32_t object_instance, + BACNET_PROPERTY_ID object_property, int32_t array_index) { - BACNET_ADDRESS dest; - BACNET_ADDRESS my_address; - unsigned max_apdu = 0; - uint8_t invoke_id = 0; - bool status = false; - int pdu_len = 0; - int bytes_sent = 0; - BACNET_READ_PROPERTY_DATA data; + BACNET_ADDRESS dest; + BACNET_ADDRESS my_address; + unsigned max_apdu = 0; + uint8_t invoke_id = 0; + bool status = false; + int pdu_len = 0; + int bytes_sent = 0; + BACNET_READ_PROPERTY_DATA data; - if (!dcc_communication_enabled()) - return 0; + if (!dcc_communication_enabled()) + return 0; - /* is the device bound? */ - status = address_get_by_device(device_id, &max_apdu, &dest); - /* is there a tsm available? */ - if (status) - status = tsm_transaction_available(); - if (status) - { - datalink_get_my_address(&my_address); - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - &my_address, - true, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); + /* is the device bound? */ + status = address_get_by_device(device_id, &max_apdu, &dest); + /* is there a tsm available? */ + if (status) + status = tsm_transaction_available(); + if (status) { + datalink_get_my_address(&my_address); + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, &my_address, true, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); - invoke_id = tsm_next_free_invokeID(); - // load the data for the encoding - data.object_type = object_type; - data.object_instance = object_instance; - data.object_property = object_property; - data.array_index = array_index; - pdu_len += rp_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - invoke_id, - &data); - /* will it fit in the sender? - note: if there is a bottleneck router in between - us and the destination, we won't know unless - we have a way to check for that and update the - max_apdu in the address binding table. */ - if ((unsigned)pdu_len < max_apdu) - { - tsm_set_confirmed_unsegmented_transaction( - invoke_id, - &dest, - &Handler_Transmit_Buffer[0], - pdu_len); - bytes_sent = datalink_send_pdu( - &dest, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send ReadProperty Request (%s)!\n", - strerror(errno)); + invoke_id = tsm_next_free_invokeID(); + // load the data for the encoding + data.object_type = object_type; + data.object_instance = object_instance; + data.object_property = object_property; + data.array_index = array_index; + pdu_len += rp_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + invoke_id, &data); + /* will it fit in the sender? + note: if there is a bottleneck router in between + us and the destination, we won't know unless + we have a way to check for that and update the + max_apdu in the address binding table. */ + if ((unsigned) pdu_len < max_apdu) { + tsm_set_confirmed_unsegmented_transaction(invoke_id, + &dest, &Handler_Transmit_Buffer[0], pdu_len); + bytes_sent = datalink_send_pdu(&dest, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, + "Failed to Send ReadProperty Request (%s)!\n", + strerror(errno)); + } else + fprintf(stderr, "Failed to Send ReadProperty Request " + "(exceeds destination maximum APDU)!\n"); } - else - fprintf(stderr,"Failed to Send ReadProperty Request " - "(exceeds destination maximum APDU)!\n"); - } - return invoke_id; + return invoke_id; } diff --git a/bacnet-stack/demo/handler/s_whohas.c b/bacnet-stack/demo/handler/s_whohas.c index 916269b4..97321a29 100644 --- a/bacnet-stack/demo/handler/s_whohas.c +++ b/bacnet-stack/demo/handler/s_whohas.c @@ -43,83 +43,67 @@ #include "txbuf.h" /* find a specific device, or use -1 for limit if you want unlimited */ -void Send_WhoHas_Name( - int32_t low_limit, - int32_t high_limit, - char *object_name) +void Send_WhoHas_Name(int32_t low_limit, + int32_t high_limit, char *object_name) { - int pdu_len = 0; - BACNET_ADDRESS dest; - int bytes_sent = 0; - BACNET_WHO_HAS_DATA data; + int pdu_len = 0; + BACNET_ADDRESS dest; + int bytes_sent = 0; + BACNET_WHO_HAS_DATA data; - /* if we are forbidden to send, don't send! */ - if (!dcc_communication_enabled()) - return; - /* Who-Has is a global broadcast */ - datalink_get_broadcast_address(&dest); - /* encode the NPDU portion of the packet */ - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - NULL, - false, /* true for confirmed messages */ - MESSAGE_PRIORITY_NORMAL); - /* encode the APDU portion of the packet */ - data.low_limit = low_limit; - data.high_limit = high_limit; - data.object_name = true; - characterstring_init_ansi(&data.object.name,object_name); - pdu_len += whohas_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - &data); - /* send the data */ - bytes_sent = datalink_send_pdu( - &dest, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send Who-Has Request (%s)!\n", strerror(errno)); + /* if we are forbidden to send, don't send! */ + if (!dcc_communication_enabled()) + return; + /* Who-Has is a global broadcast */ + datalink_get_broadcast_address(&dest); + /* encode the NPDU portion of the packet */ + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, NULL, false, /* true for confirmed messages */ + MESSAGE_PRIORITY_NORMAL); + /* encode the APDU portion of the packet */ + data.low_limit = low_limit; + data.high_limit = high_limit; + data.object_name = true; + characterstring_init_ansi(&data.object.name, object_name); + pdu_len += whohas_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + &data); + /* send the data */ + bytes_sent = datalink_send_pdu(&dest, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, "Failed to Send Who-Has Request (%s)!\n", + strerror(errno)); } /* find a specific device, or use -1 for limit if you want unlimited */ -void Send_WhoHas_Object( - int32_t low_limit, - int32_t high_limit, - BACNET_OBJECT_TYPE object_type, - uint32_t object_instance) +void Send_WhoHas_Object(int32_t low_limit, + int32_t high_limit, + BACNET_OBJECT_TYPE object_type, uint32_t object_instance) { - int pdu_len = 0; - BACNET_ADDRESS dest; - int bytes_sent = 0; - BACNET_WHO_HAS_DATA data; + int pdu_len = 0; + BACNET_ADDRESS dest; + int bytes_sent = 0; + BACNET_WHO_HAS_DATA data; - /* if we are forbidden to send, don't send! */ - if (!dcc_communication_enabled()) - return; - /* Who-Has is a global broadcast */ - datalink_get_broadcast_address(&dest); - /* encode the NPDU portion of the packet */ - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - NULL, - false, /* true for confirmed messages */ - MESSAGE_PRIORITY_NORMAL); - /* encode the APDU portion of the packet */ - data.low_limit = low_limit; - data.high_limit = high_limit; - data.object_name = false; - data.object.identifier.type = object_type; - data.object.identifier.instance = object_instance; - pdu_len += whohas_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - &data); - /* send the data */ - bytes_sent = datalink_send_pdu( - &dest, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send Who-Has Request (%s)!\n", strerror(errno)); + /* if we are forbidden to send, don't send! */ + if (!dcc_communication_enabled()) + return; + /* Who-Has is a global broadcast */ + datalink_get_broadcast_address(&dest); + /* encode the NPDU portion of the packet */ + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, NULL, false, /* true for confirmed messages */ + MESSAGE_PRIORITY_NORMAL); + /* encode the APDU portion of the packet */ + data.low_limit = low_limit; + data.high_limit = high_limit; + data.object_name = false; + data.object.identifier.type = object_type; + data.object.identifier.instance = object_instance; + pdu_len += whohas_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + &data); + /* send the data */ + bytes_sent = datalink_send_pdu(&dest, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, "Failed to Send Who-Has Request (%s)!\n", + strerror(errno)); } diff --git a/bacnet-stack/demo/handler/s_whois.c b/bacnet-stack/demo/handler/s_whois.c index 680a659f..1ad07246 100644 --- a/bacnet-stack/demo/handler/s_whois.c +++ b/bacnet-stack/demo/handler/s_whois.c @@ -43,38 +43,29 @@ #include "txbuf.h" /* find a specific device, or use -1 for limit if you want unlimited */ -void Send_WhoIs( - int32_t low_limit, - int32_t high_limit) +void Send_WhoIs(int32_t low_limit, int32_t high_limit) { - int pdu_len = 0; - BACNET_ADDRESS dest; - int bytes_sent = 0; + int pdu_len = 0; + BACNET_ADDRESS dest; + int bytes_sent = 0; - if (!dcc_communication_enabled()) - return; + if (!dcc_communication_enabled()) + return; - // Who-Is is a global broadcast - datalink_get_broadcast_address(&dest); + // Who-Is is a global broadcast + datalink_get_broadcast_address(&dest); - // encode the NPDU portion of the packet - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - NULL, - false, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); + // encode the NPDU portion of the packet + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, NULL, false, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); - // encode the APDU portion of the packet - pdu_len += whois_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - low_limit, - high_limit); + // encode the APDU portion of the packet + pdu_len += whois_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + low_limit, high_limit); - bytes_sent = datalink_send_pdu( - &dest, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send Who-Is Request (%s)!\n", strerror(errno)); + bytes_sent = datalink_send_pdu(&dest, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, "Failed to Send Who-Is Request (%s)!\n", + strerror(errno)); } diff --git a/bacnet-stack/demo/handler/s_wp.c b/bacnet-stack/demo/handler/s_wp.c index 05d333c7..fc7a7a24 100644 --- a/bacnet-stack/demo/handler/s_wp.c +++ b/bacnet-stack/demo/handler/s_wp.c @@ -43,79 +43,63 @@ #include "txbuf.h" /* returns the invoke ID for confirmed request, or zero on failure */ -uint8_t Send_Write_Property_Request( - uint32_t device_id, // destination device - BACNET_OBJECT_TYPE object_type, - uint32_t object_instance, - BACNET_PROPERTY_ID object_property, - BACNET_APPLICATION_DATA_VALUE *object_value, - uint8_t priority, - int32_t array_index) +uint8_t Send_Write_Property_Request(uint32_t device_id, // destination device + BACNET_OBJECT_TYPE object_type, + uint32_t object_instance, + BACNET_PROPERTY_ID object_property, + BACNET_APPLICATION_DATA_VALUE * object_value, + uint8_t priority, int32_t array_index) { - BACNET_ADDRESS dest; - BACNET_ADDRESS my_address; - unsigned max_apdu = 0; - uint8_t invoke_id = 0; - bool status = false; - int pdu_len = 0; - int bytes_sent = 0; - BACNET_WRITE_PROPERTY_DATA data; + BACNET_ADDRESS dest; + BACNET_ADDRESS my_address; + unsigned max_apdu = 0; + uint8_t invoke_id = 0; + bool status = false; + int pdu_len = 0; + int bytes_sent = 0; + BACNET_WRITE_PROPERTY_DATA data; - if (!dcc_communication_enabled()) - return 0; + if (!dcc_communication_enabled()) + return 0; - /* is the device bound? */ - status = address_get_by_device(device_id, &max_apdu, &dest); - /* is there a tsm available? */ - if (status) - status = tsm_transaction_available(); - if (status) - { - datalink_get_my_address(&my_address); - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - &my_address, - true, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); + /* is the device bound? */ + status = address_get_by_device(device_id, &max_apdu, &dest); + /* is there a tsm available? */ + if (status) + status = tsm_transaction_available(); + if (status) { + datalink_get_my_address(&my_address); + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, &my_address, true, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); - invoke_id = tsm_next_free_invokeID(); - // load the data for the encoding - data.object_type = object_type; - data.object_instance = object_instance; - data.object_property = object_property; - data.array_index = array_index; - bacapp_copy(&data.value,object_value); - data.priority = priority; - pdu_len += wp_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - invoke_id, - &data); - /* will it fit in the sender? - note: if there is a bottleneck router in between - us and the destination, we won't know unless - we have a way to check for that and update the - max_apdu in the address binding table. */ - if ((unsigned)pdu_len < max_apdu) - { - tsm_set_confirmed_unsegmented_transaction( - invoke_id, - &dest, - &Handler_Transmit_Buffer[0], - pdu_len); - bytes_sent = datalink_send_pdu( - &dest, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send WriteProperty Request (%s)!\n", - strerror(errno)); + invoke_id = tsm_next_free_invokeID(); + // load the data for the encoding + data.object_type = object_type; + data.object_instance = object_instance; + data.object_property = object_property; + data.array_index = array_index; + bacapp_copy(&data.value, object_value); + data.priority = priority; + pdu_len += wp_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + invoke_id, &data); + /* will it fit in the sender? + note: if there is a bottleneck router in between + us and the destination, we won't know unless + we have a way to check for that and update the + max_apdu in the address binding table. */ + if ((unsigned) pdu_len < max_apdu) { + tsm_set_confirmed_unsegmented_transaction(invoke_id, + &dest, &Handler_Transmit_Buffer[0], pdu_len); + bytes_sent = datalink_send_pdu(&dest, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, + "Failed to Send WriteProperty Request (%s)!\n", + strerror(errno)); + } else + fprintf(stderr, "Failed to Send WriteProperty Request " + "(exceeds destination maximum APDU)!\n"); } - else - fprintf(stderr,"Failed to Send WriteProperty Request " - "(exceeds destination maximum APDU)!\n"); - } - return invoke_id; + return invoke_id; } - diff --git a/bacnet-stack/demo/handler/txbuf.c b/bacnet-stack/demo/handler/txbuf.c index 1b60d630..25a50b53 100644 --- a/bacnet-stack/demo/handler/txbuf.c +++ b/bacnet-stack/demo/handler/txbuf.c @@ -27,5 +27,4 @@ #include "config.h" #include "datalink.h" -uint8_t Handler_Transmit_Buffer[MAX_MPDU] = {0}; - +uint8_t Handler_Transmit_Buffer[MAX_MPDU] = { 0 }; diff --git a/bacnet-stack/demo/object/ai.c b/bacnet-stack/demo/object/ai.c index f8a57df7..fafda408 100644 --- a/bacnet-stack/demo/object/ai.c +++ b/bacnet-stack/demo/object/ai.c @@ -31,7 +31,7 @@ #include "bacdef.h" #include "bacdcode.h" #include "bacenum.h" -#include "config.h" // the custom stuff +#include "config.h" // the custom stuff #define MAX_ANALOG_INPUTS 7 @@ -40,17 +40,17 @@ // given instance exists bool Analog_Input_Valid_Instance(uint32_t object_instance) { - if (object_instance < MAX_ANALOG_INPUTS) - return true; + if (object_instance < MAX_ANALOG_INPUTS) + return true; - return false; + return false; } // we simply have 0-n object instances. Yours might be // more complex, and then count how many you have unsigned Analog_Input_Count(void) { - return MAX_ANALOG_INPUTS; + return MAX_ANALOG_INPUTS; } // we simply have 0-n object instances. Yours might be @@ -58,81 +58,77 @@ unsigned Analog_Input_Count(void) // that correlates to the correct index uint32_t Analog_Input_Index_To_Instance(unsigned index) { - return index; + return index; } char *Analog_Input_Name(uint32_t object_instance) { - static char text_string[32] = ""; /* okay for single thread */ - - if (object_instance < MAX_ANALOG_INPUTS) - { - sprintf(text_string,"ANALOG INPUT %u",object_instance); - return text_string; - } + static char text_string[32] = ""; /* okay for single thread */ - return NULL; + if (object_instance < MAX_ANALOG_INPUTS) { + sprintf(text_string, "ANALOG INPUT %u", object_instance); + return text_string; + } + + return NULL; } /* return apdu length, or -1 on error */ /* assumption - object has already exists */ -int Analog_Input_Encode_Property_APDU( - uint8_t *apdu, - uint32_t object_instance, - BACNET_PROPERTY_ID property, - int32_t array_index, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code) +int Analog_Input_Encode_Property_APDU(uint8_t * apdu, + uint32_t object_instance, + BACNET_PROPERTY_ID property, + int32_t array_index, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code) { - int apdu_len = 0; // return value - BACNET_BIT_STRING bit_string; - BACNET_CHARACTER_STRING char_string; - float value = 3.14; - - (void)array_index; - switch (property) - { + int apdu_len = 0; // return value + BACNET_BIT_STRING bit_string; + BACNET_CHARACTER_STRING char_string; + float value = 3.14; + + (void) array_index; + switch (property) { case PROP_OBJECT_IDENTIFIER: - apdu_len = encode_tagged_object_id(&apdu[0], OBJECT_ANALOG_INPUT, - object_instance); - break; + apdu_len = encode_tagged_object_id(&apdu[0], OBJECT_ANALOG_INPUT, + object_instance); + break; case PROP_OBJECT_NAME: case PROP_DESCRIPTION: - characterstring_init_ansi(&char_string, Analog_Input_Name(object_instance)); - apdu_len = encode_tagged_character_string(&apdu[0], - &char_string); - break; + characterstring_init_ansi(&char_string, + Analog_Input_Name(object_instance)); + apdu_len = encode_tagged_character_string(&apdu[0], &char_string); + break; case PROP_OBJECT_TYPE: - apdu_len = encode_tagged_enumerated(&apdu[0], OBJECT_ANALOG_INPUT); - break; + apdu_len = encode_tagged_enumerated(&apdu[0], OBJECT_ANALOG_INPUT); + break; case PROP_PRESENT_VALUE: - apdu_len = encode_tagged_real(&apdu[0], value); - break; + apdu_len = encode_tagged_real(&apdu[0], value); + break; case PROP_STATUS_FLAGS: - bitstring_init(&bit_string); - bitstring_set_bit(&bit_string, STATUS_FLAG_IN_ALARM, false); - bitstring_set_bit(&bit_string, STATUS_FLAG_FAULT, false); - bitstring_set_bit(&bit_string, STATUS_FLAG_OVERRIDDEN, false); - bitstring_set_bit(&bit_string, STATUS_FLAG_OUT_OF_SERVICE, false); - apdu_len = encode_tagged_bitstring(&apdu[0], &bit_string); - break; + bitstring_init(&bit_string); + bitstring_set_bit(&bit_string, STATUS_FLAG_IN_ALARM, false); + bitstring_set_bit(&bit_string, STATUS_FLAG_FAULT, false); + bitstring_set_bit(&bit_string, STATUS_FLAG_OVERRIDDEN, false); + bitstring_set_bit(&bit_string, STATUS_FLAG_OUT_OF_SERVICE, false); + apdu_len = encode_tagged_bitstring(&apdu[0], &bit_string); + break; case PROP_EVENT_STATE: - apdu_len = encode_tagged_enumerated(&apdu[0],EVENT_STATE_NORMAL); - break; + apdu_len = encode_tagged_enumerated(&apdu[0], EVENT_STATE_NORMAL); + break; case PROP_OUT_OF_SERVICE: - apdu_len = encode_tagged_boolean(&apdu[0],false); - break; + apdu_len = encode_tagged_boolean(&apdu[0], false); + break; case PROP_UNITS: - apdu_len = encode_tagged_enumerated(&apdu[0],UNITS_PERCENT); - break; + apdu_len = encode_tagged_enumerated(&apdu[0], UNITS_PERCENT); + break; default: - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_UNKNOWN_PROPERTY; - apdu_len = -1; - break; - } + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_UNKNOWN_PROPERTY; + apdu_len = -1; + break; + } - return apdu_len; + return apdu_len; } #ifdef TEST @@ -142,34 +138,31 @@ int Analog_Input_Encode_Property_APDU( void testAnalogInput(Test * pTest) { - uint8_t apdu[MAX_APDU] = { 0 }; - int len = 0; - uint32_t len_value = 0; - uint8_t tag_number = 0; - BACNET_OBJECT_TYPE decoded_type = OBJECT_ANALOG_OUTPUT; - uint32_t decoded_instance = 0; - uint32_t instance = 123; - BACNET_ERROR_CLASS error_class; - BACNET_ERROR_CODE error_code; + uint8_t apdu[MAX_APDU] = { 0 }; + int len = 0; + uint32_t len_value = 0; + uint8_t tag_number = 0; + BACNET_OBJECT_TYPE decoded_type = OBJECT_ANALOG_OUTPUT; + uint32_t decoded_instance = 0; + uint32_t instance = 123; + BACNET_ERROR_CLASS error_class; + BACNET_ERROR_CODE error_code; - // FIXME: we should do a lot more testing here... - len = Analog_Input_Encode_Property_APDU( - &apdu[0], - instance, - PROP_OBJECT_IDENTIFIER, - BACNET_ARRAY_ALL, - &error_class, - &error_code); - ct_test(pTest, len >= 0); - len = decode_tag_number_and_value(&apdu[0], &tag_number, &len_value); - ct_test(pTest, tag_number == BACNET_APPLICATION_TAG_OBJECT_ID); - len = decode_object_id(&apdu[len], + // FIXME: we should do a lot more testing here... + len = Analog_Input_Encode_Property_APDU(&apdu[0], + instance, + PROP_OBJECT_IDENTIFIER, + BACNET_ARRAY_ALL, &error_class, &error_code); + ct_test(pTest, len >= 0); + len = decode_tag_number_and_value(&apdu[0], &tag_number, &len_value); + ct_test(pTest, tag_number == BACNET_APPLICATION_TAG_OBJECT_ID); + len = decode_object_id(&apdu[len], (int *) &decoded_type, &decoded_instance); - ct_test(pTest, decoded_type == OBJECT_ANALOG_INPUT); - ct_test(pTest, decoded_instance == instance); + ct_test(pTest, decoded_type == OBJECT_ANALOG_INPUT); + ct_test(pTest, decoded_instance == instance); - return; + return; } #ifdef TEST_ANALOG_INPUT @@ -192,5 +185,3 @@ int main(void) } #endif /* TEST_ANALOG_INPUT */ #endif /* TEST */ - - diff --git a/bacnet-stack/demo/object/ai.h b/bacnet-stack/demo/object/ai.h index 09e3a447..d940be71 100644 --- a/bacnet-stack/demo/object/ai.h +++ b/bacnet-stack/demo/object/ai.h @@ -31,28 +31,25 @@ #ifdef __cplusplus extern "C" { -#endif /* __cplusplus */ +#endif /* __cplusplus */ -bool Analog_Input_Valid_Instance(uint32_t object_instance); -unsigned Analog_Input_Count(void); -uint32_t Analog_Input_Index_To_Instance(unsigned index); -char *Analog_Input_Name(uint32_t object_instance); + bool Analog_Input_Valid_Instance(uint32_t object_instance); + unsigned Analog_Input_Count(void); + uint32_t Analog_Input_Index_To_Instance(unsigned index); + char *Analog_Input_Name(uint32_t object_instance); -int Analog_Input_Encode_Property_APDU( - uint8_t *apdu, - uint32_t object_instance, - BACNET_PROPERTY_ID property, - int32_t array_index, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code); + int Analog_Input_Encode_Property_APDU(uint8_t * apdu, + uint32_t object_instance, + BACNET_PROPERTY_ID property, + int32_t array_index, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code); #ifdef TEST #include "ctest.h" -void testAnalogInput(Test * pTest); + void testAnalogInput(Test * pTest); #endif #ifdef __cplusplus } -#endif /* __cplusplus */ - +#endif /* __cplusplus */ #endif diff --git a/bacnet-stack/demo/object/ao.c b/bacnet-stack/demo/object/ao.c index 59dc3bcf..1490b376 100644 --- a/bacnet-stack/demo/object/ao.c +++ b/bacnet-stack/demo/object/ao.c @@ -31,7 +31,7 @@ #include "bacdef.h" #include "bacdcode.h" #include "bacenum.h" -#include "config.h" // the custom stuff +#include "config.h" // the custom stuff #include "wp.h" #define MAX_ANALOG_OUTPUTS 4 @@ -46,7 +46,8 @@ // Here is our Priority Array. They are supposed to be Real, but // we don't have that kind of memory, so we will use a single byte // and load a Real for returning the value when asked. -static uint8_t Analog_Output_Level[MAX_ANALOG_OUTPUTS][BACNET_MAX_PRIORITY]; +static uint8_t + Analog_Output_Level[MAX_ANALOG_OUTPUTS][BACNET_MAX_PRIORITY]; // Writable out-of-service allows others to play with our Present Value // without changing the physical output static bool Analog_Output_Out_Of_Service[MAX_ANALOG_OUTPUTS]; @@ -56,23 +57,20 @@ static bool Analog_Ouput_Initialized = false; void Analog_Output_Init(void) { - unsigned i,j; + unsigned i, j; - if (!Analog_Ouput_Initialized) - { - Analog_Ouput_Initialized = true; - - // initialize all the analog output priority arrays to NULL - for (i = 0; i < MAX_ANALOG_OUTPUTS; i++) - { - for (j = 0; j < BACNET_MAX_PRIORITY; j++) - { - Analog_Output_Level[i][j] = AO_LEVEL_NULL; - } + if (!Analog_Ouput_Initialized) { + Analog_Ouput_Initialized = true; + + // initialize all the analog output priority arrays to NULL + for (i = 0; i < MAX_ANALOG_OUTPUTS; i++) { + for (j = 0; j < BACNET_MAX_PRIORITY; j++) { + Analog_Output_Level[i][j] = AO_LEVEL_NULL; + } + } } - } - - return; + + return; } // we simply have 0-n object instances. Yours might be @@ -80,19 +78,19 @@ void Analog_Output_Init(void) // given instance exists bool Analog_Output_Valid_Instance(uint32_t object_instance) { - Analog_Output_Init(); - if (object_instance < MAX_ANALOG_OUTPUTS) - return true; + Analog_Output_Init(); + if (object_instance < MAX_ANALOG_OUTPUTS) + return true; - return false; + return false; } // we simply have 0-n object instances. Yours might be // more complex, and then count how many you have unsigned Analog_Output_Count(void) { - Analog_Output_Init(); - return MAX_ANALOG_OUTPUTS; + Analog_Output_Init(); + return MAX_ANALOG_OUTPUTS; } // we simply have 0-n object instances. Yours might be @@ -100,8 +98,8 @@ unsigned Analog_Output_Count(void) // that correlates to the correct index uint32_t Analog_Output_Index_To_Instance(unsigned index) { - Analog_Output_Init(); - return index; + Analog_Output_Init(); + return index; } // we simply have 0-n object instances. Yours might be @@ -109,271 +107,240 @@ uint32_t Analog_Output_Index_To_Instance(unsigned index) // that correlates to the correct instance number unsigned Analog_Output_Instance_To_Index(uint32_t object_instance) { - unsigned index = MAX_ANALOG_OUTPUTS; + unsigned index = MAX_ANALOG_OUTPUTS; - Analog_Output_Init(); - if (object_instance < MAX_ANALOG_OUTPUTS) - index = object_instance; - - return index; + Analog_Output_Init(); + if (object_instance < MAX_ANALOG_OUTPUTS) + index = object_instance; + + return index; } static float Analog_Output_Present_Value(uint32_t object_instance) { - float value = AO_RELINQUISH_DEFAULT; - unsigned index = 0; - unsigned i = 0; + float value = AO_RELINQUISH_DEFAULT; + unsigned index = 0; + unsigned i = 0; - Analog_Output_Init(); - index = Analog_Output_Instance_To_Index(object_instance); - if (index < MAX_ANALOG_OUTPUTS) - { - for (i = 0; i < BACNET_MAX_PRIORITY; i++) - { - if (Analog_Output_Level[index][i] != AO_LEVEL_NULL) - { - value = Analog_Output_Level[index][i]; - break; - } + Analog_Output_Init(); + index = Analog_Output_Instance_To_Index(object_instance); + if (index < MAX_ANALOG_OUTPUTS) { + for (i = 0; i < BACNET_MAX_PRIORITY; i++) { + if (Analog_Output_Level[index][i] != AO_LEVEL_NULL) { + value = Analog_Output_Level[index][i]; + break; + } + } } - } - - return value; + + return value; } /* note: the object name must be unique within this device */ char *Analog_Output_Name(uint32_t object_instance) { - static char text_string[32] = ""; /* okay for single thread */ - - if (object_instance < MAX_ANALOG_OUTPUTS) - { - sprintf(text_string,"ANALOG OUTPUT %u",object_instance); - return text_string; - } + static char text_string[32] = ""; /* okay for single thread */ - return NULL; + if (object_instance < MAX_ANALOG_OUTPUTS) { + sprintf(text_string, "ANALOG OUTPUT %u", object_instance); + return text_string; + } + + return NULL; } /* return apdu len, or -1 on error */ -int Analog_Output_Encode_Property_APDU( - uint8_t *apdu, - uint32_t object_instance, - BACNET_PROPERTY_ID property, - int32_t array_index, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code) +int Analog_Output_Encode_Property_APDU(uint8_t * apdu, + uint32_t object_instance, + BACNET_PROPERTY_ID property, + int32_t array_index, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code) { - int len = 0; - int apdu_len = 0; // return value - BACNET_BIT_STRING bit_string; - BACNET_CHARACTER_STRING char_string; - float real_value = 1.414; - unsigned object_index = 0; - unsigned i = 0; - - Analog_Output_Init(); - switch (property) - { + int len = 0; + int apdu_len = 0; // return value + BACNET_BIT_STRING bit_string; + BACNET_CHARACTER_STRING char_string; + float real_value = 1.414; + unsigned object_index = 0; + unsigned i = 0; + + Analog_Output_Init(); + switch (property) { case PROP_OBJECT_IDENTIFIER: - apdu_len = encode_tagged_object_id(&apdu[0], OBJECT_ANALOG_OUTPUT, - object_instance); - break; + apdu_len = encode_tagged_object_id(&apdu[0], OBJECT_ANALOG_OUTPUT, + object_instance); + break; case PROP_OBJECT_NAME: case PROP_DESCRIPTION: - characterstring_init_ansi(&char_string, Analog_Output_Name(object_instance)); - apdu_len = encode_tagged_character_string(&apdu[0], - &char_string); - break; + characterstring_init_ansi(&char_string, + Analog_Output_Name(object_instance)); + apdu_len = encode_tagged_character_string(&apdu[0], &char_string); + break; case PROP_OBJECT_TYPE: - apdu_len = encode_tagged_enumerated(&apdu[0], OBJECT_ANALOG_OUTPUT); - break; + apdu_len = + encode_tagged_enumerated(&apdu[0], OBJECT_ANALOG_OUTPUT); + break; case PROP_PRESENT_VALUE: - real_value = Analog_Output_Present_Value(object_instance); - apdu_len = encode_tagged_real(&apdu[0], real_value); - break; + real_value = Analog_Output_Present_Value(object_instance); + apdu_len = encode_tagged_real(&apdu[0], real_value); + break; case PROP_STATUS_FLAGS: - bitstring_init(&bit_string); - bitstring_set_bit(&bit_string, STATUS_FLAG_IN_ALARM, false); - bitstring_set_bit(&bit_string, STATUS_FLAG_FAULT, false); - bitstring_set_bit(&bit_string, STATUS_FLAG_OVERRIDDEN, false); - bitstring_set_bit(&bit_string, STATUS_FLAG_OUT_OF_SERVICE, false); - apdu_len = encode_tagged_bitstring(&apdu[0], &bit_string); - break; + bitstring_init(&bit_string); + bitstring_set_bit(&bit_string, STATUS_FLAG_IN_ALARM, false); + bitstring_set_bit(&bit_string, STATUS_FLAG_FAULT, false); + bitstring_set_bit(&bit_string, STATUS_FLAG_OVERRIDDEN, false); + bitstring_set_bit(&bit_string, STATUS_FLAG_OUT_OF_SERVICE, false); + apdu_len = encode_tagged_bitstring(&apdu[0], &bit_string); + break; case PROP_EVENT_STATE: - apdu_len = encode_tagged_enumerated(&apdu[0],EVENT_STATE_NORMAL); - break; + apdu_len = encode_tagged_enumerated(&apdu[0], EVENT_STATE_NORMAL); + break; case PROP_OUT_OF_SERVICE: - apdu_len = encode_tagged_boolean(&apdu[0],false); - break; + apdu_len = encode_tagged_boolean(&apdu[0], false); + break; case PROP_UNITS: - apdu_len = encode_tagged_enumerated(&apdu[0],UNITS_PERCENT); - break; + apdu_len = encode_tagged_enumerated(&apdu[0], UNITS_PERCENT); + break; case PROP_PRIORITY_ARRAY: - // Array element zero is the number of elements in the array - if (array_index == BACNET_ARRAY_LENGTH_INDEX) - apdu_len = encode_tagged_unsigned(&apdu[0], BACNET_MAX_PRIORITY); - // if no index was specified, then try to encode the entire list - // into one packet. - else if (array_index == BACNET_ARRAY_ALL) - { - object_index = Analog_Output_Instance_To_Index(object_instance); - for (i = 0; i < BACNET_MAX_PRIORITY; i++) - { - // FIXME: check if we have room before adding it to APDU - if (Analog_Output_Level[object_index][i] == AO_LEVEL_NULL) - len = encode_tagged_null(&apdu[apdu_len]); - else - { - real_value = Analog_Output_Level[object_index][i]; - len = encode_tagged_real(&apdu[apdu_len], real_value); - } - // add it if we have room - if ((apdu_len + len) < MAX_APDU) - apdu_len += len; - else - { - *error_class = ERROR_CLASS_SERVICES; - *error_code = ERROR_CODE_NO_SPACE_FOR_OBJECT; - apdu_len = -1; - break; - } + // Array element zero is the number of elements in the array + if (array_index == BACNET_ARRAY_LENGTH_INDEX) + apdu_len = + encode_tagged_unsigned(&apdu[0], BACNET_MAX_PRIORITY); + // if no index was specified, then try to encode the entire list + // into one packet. + else if (array_index == BACNET_ARRAY_ALL) { + object_index = + Analog_Output_Instance_To_Index(object_instance); + for (i = 0; i < BACNET_MAX_PRIORITY; i++) { + // FIXME: check if we have room before adding it to APDU + if (Analog_Output_Level[object_index][i] == AO_LEVEL_NULL) + len = encode_tagged_null(&apdu[apdu_len]); + else { + real_value = Analog_Output_Level[object_index][i]; + len = encode_tagged_real(&apdu[apdu_len], real_value); + } + // add it if we have room + if ((apdu_len + len) < MAX_APDU) + apdu_len += len; + else { + *error_class = ERROR_CLASS_SERVICES; + *error_code = ERROR_CODE_NO_SPACE_FOR_OBJECT; + apdu_len = -1; + break; + } + } + } else { + object_index = + Analog_Output_Instance_To_Index(object_instance); + if (array_index <= BACNET_MAX_PRIORITY) { + if (Analog_Output_Level[object_index][array_index] == + AO_LEVEL_NULL) + len = encode_tagged_null(&apdu[apdu_len]); + else { + real_value = + Analog_Output_Level[object_index][array_index]; + len = encode_tagged_real(&apdu[apdu_len], real_value); + } + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_INVALID_ARRAY_INDEX; + apdu_len = -1; + } } - } - else - { - object_index = Analog_Output_Instance_To_Index(object_instance); - if (array_index <= BACNET_MAX_PRIORITY) - { - if (Analog_Output_Level[object_index][array_index] == AO_LEVEL_NULL) - len = encode_tagged_null(&apdu[apdu_len]); - else - { - real_value = Analog_Output_Level[object_index][array_index]; - len = encode_tagged_real(&apdu[apdu_len], real_value); - } - } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_INVALID_ARRAY_INDEX; - apdu_len = -1; - } - } - - break; - case PROP_RELINQUISH_DEFAULT: - real_value = AO_RELINQUISH_DEFAULT; - apdu_len = encode_tagged_real(&apdu[0], real_value); - break; - default: - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_UNKNOWN_PROPERTY; - apdu_len = -1; - break; - } - return apdu_len; + break; + case PROP_RELINQUISH_DEFAULT: + real_value = AO_RELINQUISH_DEFAULT; + apdu_len = encode_tagged_real(&apdu[0], real_value); + break; + default: + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_UNKNOWN_PROPERTY; + apdu_len = -1; + break; + } + + return apdu_len; } // returns true if successful -bool Analog_Output_Write_Property( - BACNET_WRITE_PROPERTY_DATA *wp_data, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code) +bool Analog_Output_Write_Property(BACNET_WRITE_PROPERTY_DATA * wp_data, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code) { - bool status = false; // return value - unsigned int object_index = 0; - unsigned int priority = 0; - uint8_t level = AO_LEVEL_NULL; - - Analog_Output_Init(); - if (!Analog_Output_Valid_Instance(wp_data->object_instance)) - { - *error_class = ERROR_CLASS_OBJECT; - *error_code = ERROR_CODE_UNKNOWN_OBJECT; - return false; - } + bool status = false; // return value + unsigned int object_index = 0; + unsigned int priority = 0; + uint8_t level = AO_LEVEL_NULL; - // decode the some of the request - switch (wp_data->object_property) - { + Analog_Output_Init(); + if (!Analog_Output_Valid_Instance(wp_data->object_instance)) { + *error_class = ERROR_CLASS_OBJECT; + *error_code = ERROR_CODE_UNKNOWN_OBJECT; + return false; + } + // decode the some of the request + switch (wp_data->object_property) { case PROP_PRESENT_VALUE: - if (wp_data->value.tag == BACNET_APPLICATION_TAG_REAL) - { - priority = wp_data->priority; - if (priority && (priority <= BACNET_MAX_PRIORITY) && - (priority != 6 /* reserved */) && - (wp_data->value.type.Real >= 0.0) && - (wp_data->value.type.Real <= 100.0)) - { - level = (uint8_t)wp_data->value.type.Real; - object_index = Analog_Output_Instance_To_Index( - wp_data->object_instance); - priority--; - Analog_Output_Level[object_index][priority] = level; - // if Out of Service is TRUE, then don't set the - // physical output. This comment may apply to the - // main loop (i.e. check out of service before changing output) - status = true; + if (wp_data->value.tag == BACNET_APPLICATION_TAG_REAL) { + priority = wp_data->priority; + if (priority && (priority <= BACNET_MAX_PRIORITY) && + (priority != 6 /* reserved */ ) && + (wp_data->value.type.Real >= 0.0) && + (wp_data->value.type.Real <= 100.0)) { + level = (uint8_t) wp_data->value.type.Real; + object_index = + Analog_Output_Instance_To_Index(wp_data-> + object_instance); + priority--; + Analog_Output_Level[object_index][priority] = level; + // if Out of Service is TRUE, then don't set the + // physical output. This comment may apply to the + // main loop (i.e. check out of service before changing output) + status = true; + } else if (priority == 6) { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_WRITE_ACCESS_DENIED; + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_VALUE_OUT_OF_RANGE; + } + } else if (wp_data->value.tag == BACNET_APPLICATION_TAG_NULL) { + level = AO_LEVEL_NULL; + object_index = + Analog_Output_Instance_To_Index(wp_data->object_instance); + priority = wp_data->priority; + if (priority && (priority <= BACNET_MAX_PRIORITY)) { + priority--; + Analog_Output_Level[object_index][priority] = level; + status = true; + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_VALUE_OUT_OF_RANGE; + } + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_INVALID_DATA_TYPE; } - else if (priority == 6) - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_WRITE_ACCESS_DENIED; - } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_VALUE_OUT_OF_RANGE; - } - } - else if (wp_data->value.tag == BACNET_APPLICATION_TAG_NULL) - { - level = AO_LEVEL_NULL; - object_index = Analog_Output_Instance_To_Index( - wp_data->object_instance); - priority = wp_data->priority; - if (priority && (priority <= BACNET_MAX_PRIORITY)) - { - priority--; - Analog_Output_Level[object_index][priority] = level; - status = true; - } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_VALUE_OUT_OF_RANGE; - } - } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_INVALID_DATA_TYPE; - } - break; + break; case PROP_OUT_OF_SERVICE: - if (wp_data->value.tag == BACNET_APPLICATION_TAG_BOOLEAN) - { - object_index = Analog_Output_Instance_To_Index( - wp_data->object_instance); - Analog_Output_Out_Of_Service[object_index] = - wp_data->value.type.Boolean; - status = true; - } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_INVALID_DATA_TYPE; - } - break; + if (wp_data->value.tag == BACNET_APPLICATION_TAG_BOOLEAN) { + object_index = + Analog_Output_Instance_To_Index(wp_data->object_instance); + Analog_Output_Out_Of_Service[object_index] = + wp_data->value.type.Boolean; + status = true; + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_INVALID_DATA_TYPE; + } + break; default: - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_WRITE_ACCESS_DENIED; - break; - } + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_WRITE_ACCESS_DENIED; + break; + } - return status; + return status; } @@ -384,33 +351,30 @@ bool Analog_Output_Write_Property( void testAnalogOutput(Test * pTest) { - uint8_t apdu[MAX_APDU] = { 0 }; - int len = 0; - uint32_t len_value = 0; - uint8_t tag_number = 0; - BACNET_OBJECT_TYPE decoded_type = OBJECT_ANALOG_OUTPUT; - uint32_t decoded_instance = 0; - uint32_t instance = 123; - BACNET_ERROR_CLASS error_class; - BACNET_ERROR_CODE error_code; + uint8_t apdu[MAX_APDU] = { 0 }; + int len = 0; + uint32_t len_value = 0; + uint8_t tag_number = 0; + BACNET_OBJECT_TYPE decoded_type = OBJECT_ANALOG_OUTPUT; + uint32_t decoded_instance = 0; + uint32_t instance = 123; + BACNET_ERROR_CLASS error_class; + BACNET_ERROR_CODE error_code; - - len = Analog_Output_Encode_Property_APDU( - &apdu[0], - instance, - PROP_OBJECT_IDENTIFIER, - BACNET_ARRAY_ALL, - &error_class, - &error_code); - ct_test(pTest, len != 0); - len = decode_tag_number_and_value(&apdu[0], &tag_number, &len_value); - ct_test(pTest, tag_number == BACNET_APPLICATION_TAG_OBJECT_ID); - len = decode_object_id(&apdu[len], + + len = Analog_Output_Encode_Property_APDU(&apdu[0], + instance, + PROP_OBJECT_IDENTIFIER, + BACNET_ARRAY_ALL, &error_class, &error_code); + ct_test(pTest, len != 0); + len = decode_tag_number_and_value(&apdu[0], &tag_number, &len_value); + ct_test(pTest, tag_number == BACNET_APPLICATION_TAG_OBJECT_ID); + len = decode_object_id(&apdu[len], (int *) &decoded_type, &decoded_instance); - ct_test(pTest, decoded_type == OBJECT_ANALOG_OUTPUT); - ct_test(pTest, decoded_instance == instance); + ct_test(pTest, decoded_type == OBJECT_ANALOG_OUTPUT); + ct_test(pTest, decoded_instance == instance); - return; + return; } #ifdef TEST_ANALOG_OUTPUT @@ -433,5 +397,3 @@ int main(void) } #endif /* TEST_ANALOG_INPUT */ #endif /* TEST */ - - diff --git a/bacnet-stack/demo/object/ao.h b/bacnet-stack/demo/object/ao.h index bd8bfea0..56fcc7fa 100644 --- a/bacnet-stack/demo/object/ao.h +++ b/bacnet-stack/demo/object/ao.h @@ -33,33 +33,28 @@ #ifdef __cplusplus extern "C" { -#endif /* __cplusplus */ +#endif /* __cplusplus */ -bool Analog_Output_Valid_Instance(uint32_t object_instance); -unsigned Analog_Output_Count(void); -uint32_t Analog_Output_Index_To_Instance(unsigned index); -char *Analog_Output_Name(uint32_t object_instance); + bool Analog_Output_Valid_Instance(uint32_t object_instance); + unsigned Analog_Output_Count(void); + uint32_t Analog_Output_Index_To_Instance(unsigned index); + char *Analog_Output_Name(uint32_t object_instance); -int Analog_Output_Encode_Property_APDU( - uint8_t *apdu, - uint32_t object_instance, - BACNET_PROPERTY_ID property, - int32_t array_index, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code); + int Analog_Output_Encode_Property_APDU(uint8_t * apdu, + uint32_t object_instance, + BACNET_PROPERTY_ID property, + int32_t array_index, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code); -bool Analog_Output_Write_Property( - BACNET_WRITE_PROPERTY_DATA *wp_data, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code); + bool Analog_Output_Write_Property(BACNET_WRITE_PROPERTY_DATA * wp_data, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code); #ifdef TEST #include "ctest.h" -void testAnalogOutput(Test * pTest); + void testAnalogOutput(Test * pTest); #endif #ifdef __cplusplus } -#endif /* __cplusplus */ - +#endif /* __cplusplus */ #endif diff --git a/bacnet-stack/demo/object/bacfile.c b/bacnet-stack/demo/object/bacfile.c index 71442acf..fa778ece 100644 --- a/bacnet-stack/demo/object/bacfile.c +++ b/bacnet-stack/demo/object/bacfile.c @@ -39,207 +39,182 @@ #include "arf.h" #include "awf.h" -typedef struct -{ - uint32_t instance; - char *filename; +typedef struct { + uint32_t instance; + char *filename; } BACNET_FILE_LISTING; -static BACNET_FILE_LISTING BACnet_File_Listing[] = -{ - {0, "test.log"}, - {1, "script.txt"}, - {2, "bacenum.h"}, - {0, NULL} // last file indication +static BACNET_FILE_LISTING BACnet_File_Listing[] = { + {0, "test.log"}, + {1, "script.txt"}, + {2, "bacenum.h"}, + {0, NULL} // last file indication }; char *bacfile_name(uint32_t instance) { - uint32_t index = 0; - char *filename = NULL; + uint32_t index = 0; + char *filename = NULL; - // linear search for file instance match - while (BACnet_File_Listing[index].filename) - { - if (BACnet_File_Listing[index].instance == instance) - { - filename = BACnet_File_Listing[index].filename; - break; + // linear search for file instance match + while (BACnet_File_Listing[index].filename) { + if (BACnet_File_Listing[index].instance == instance) { + filename = BACnet_File_Listing[index].filename; + break; + } + index++; } - index++; - } - return filename; + return filename; } bool bacfile_valid_instance(uint32_t object_instance) { - return bacfile_name(object_instance) ? true : false; + return bacfile_name(object_instance) ? true : false; } uint32_t bacfile_count(void) { - uint32_t index = 0; + uint32_t index = 0; - // linear search for file instance match - while (BACnet_File_Listing[index].filename) - { - index++; - } + // linear search for file instance match + while (BACnet_File_Listing[index].filename) { + index++; + } - return index; + return index; } uint32_t bacfile_index_to_instance(unsigned find_index) { - uint32_t instance = BACNET_MAX_INSTANCE + 1; - uint32_t index = 0; - - // bounds checking... - while (BACnet_File_Listing[index].filename) - { - if (index == find_index) - { - instance = BACnet_File_Listing[index].instance; - break; - } - index++; - } + uint32_t instance = BACNET_MAX_INSTANCE + 1; + uint32_t index = 0; - return instance; + // bounds checking... + while (BACnet_File_Listing[index].filename) { + if (index == find_index) { + instance = BACnet_File_Listing[index].instance; + break; + } + index++; + } + + return instance; } -static long fsize(FILE *pFile) +static long fsize(FILE * pFile) { - long size = 0; - long origin = 0; + long size = 0; + long origin = 0; - if (pFile) - { - origin = ftell(pFile); - fseek(pFile, 0L, SEEK_END); - size = ftell(pFile); - fseek(pFile, origin, SEEK_SET); - } - return (size); + if (pFile) { + origin = ftell(pFile); + fseek(pFile, 0L, SEEK_END); + size = ftell(pFile); + fseek(pFile, origin, SEEK_SET); + } + return (size); } static unsigned bacfile_file_size(uint32_t object_instance) { - char *pFilename = NULL; - FILE *pFile = NULL; - unsigned file_size = 0; + char *pFilename = NULL; + FILE *pFile = NULL; + unsigned file_size = 0; - pFilename = bacfile_name(object_instance); - if (pFilename) - { - pFile = fopen(pFilename,"rb"); - if (pFile) - { - file_size = fsize(pFile); - fclose(pFile); + pFilename = bacfile_name(object_instance); + if (pFilename) { + pFile = fopen(pFilename, "rb"); + if (pFile) { + file_size = fsize(pFile); + fclose(pFile); + } } - } - - return file_size; + + return file_size; } /* return the number of bytes used, or -1 on error */ -int bacfile_encode_property_apdu( - uint8_t *apdu, - uint32_t object_instance, - BACNET_PROPERTY_ID property, - int32_t array_index, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code) +int bacfile_encode_property_apdu(uint8_t * apdu, + uint32_t object_instance, + BACNET_PROPERTY_ID property, + int32_t array_index, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code) { - int apdu_len = 0; // return value - char text_string[32] = {""}; - BACNET_CHARACTER_STRING char_string; - - (void)array_index; - switch (property) - { - case PROP_OBJECT_IDENTIFIER: - apdu_len = encode_tagged_object_id(&apdu[0], - OBJECT_FILE, - object_instance); - break; - case PROP_OBJECT_NAME: - sprintf(text_string,"FILE %d",object_instance); - characterstring_init_ansi(&char_string, text_string); - apdu_len = encode_tagged_character_string(&apdu[0], - &char_string); - break; - case PROP_OBJECT_TYPE: - apdu_len = encode_tagged_enumerated(&apdu[0], OBJECT_FILE); - break; - case PROP_DESCRIPTION: - characterstring_init_ansi(&char_string, bacfile_name(object_instance)); - apdu_len = encode_tagged_character_string(&apdu[0], - &char_string); - break; - case PROP_FILE_TYPE: - characterstring_init_ansi(&char_string, "TEXT"); - apdu_len = encode_tagged_character_string(&apdu[0], - &char_string); - break; - case PROP_FILE_SIZE: - apdu_len = encode_tagged_unsigned(&apdu[0], - bacfile_file_size(object_instance)); - break; - case PROP_MODIFICATION_DATE: - // FIXME: get the actual value - apdu_len = encode_tagged_date(&apdu[0], - 2005, - 12, - 25, - 7 /* sunday */); - // FIXME: get the actual value - apdu_len += encode_tagged_time(&apdu[apdu_len], - 12, - 0, - 0, - 0); - break; - case PROP_ARCHIVE: - // FIXME: get the actual value: note it may be inverse... - apdu_len = encode_tagged_boolean(&apdu[0],true); - break; - case PROP_READ_ONLY: - // FIXME: get the actual value - apdu_len = encode_tagged_boolean(&apdu[0],true); - break; - case PROP_FILE_ACCESS_METHOD: - apdu_len = encode_tagged_enumerated(&apdu[0],FILE_STREAM_ACCESS); - break; - default: - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_UNKNOWN_PROPERTY; - apdu_len = -1; - break; - } + int apdu_len = 0; // return value + char text_string[32] = { "" }; + BACNET_CHARACTER_STRING char_string; - return apdu_len; + (void) array_index; + switch (property) { + case PROP_OBJECT_IDENTIFIER: + apdu_len = encode_tagged_object_id(&apdu[0], + OBJECT_FILE, object_instance); + break; + case PROP_OBJECT_NAME: + sprintf(text_string, "FILE %d", object_instance); + characterstring_init_ansi(&char_string, text_string); + apdu_len = encode_tagged_character_string(&apdu[0], &char_string); + break; + case PROP_OBJECT_TYPE: + apdu_len = encode_tagged_enumerated(&apdu[0], OBJECT_FILE); + break; + case PROP_DESCRIPTION: + characterstring_init_ansi(&char_string, + bacfile_name(object_instance)); + apdu_len = encode_tagged_character_string(&apdu[0], &char_string); + break; + case PROP_FILE_TYPE: + characterstring_init_ansi(&char_string, "TEXT"); + apdu_len = encode_tagged_character_string(&apdu[0], &char_string); + break; + case PROP_FILE_SIZE: + apdu_len = encode_tagged_unsigned(&apdu[0], + bacfile_file_size(object_instance)); + break; + case PROP_MODIFICATION_DATE: + // FIXME: get the actual value + apdu_len = encode_tagged_date(&apdu[0], + 2005, 12, 25, 7 /* sunday */ ); + // FIXME: get the actual value + apdu_len += encode_tagged_time(&apdu[apdu_len], 12, 0, 0, 0); + break; + case PROP_ARCHIVE: + // FIXME: get the actual value: note it may be inverse... + apdu_len = encode_tagged_boolean(&apdu[0], true); + break; + case PROP_READ_ONLY: + // FIXME: get the actual value + apdu_len = encode_tagged_boolean(&apdu[0], true); + break; + case PROP_FILE_ACCESS_METHOD: + apdu_len = encode_tagged_enumerated(&apdu[0], FILE_STREAM_ACCESS); + break; + default: + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_UNKNOWN_PROPERTY; + apdu_len = -1; + break; + } + + return apdu_len; } uint32_t bacfile_instance(char *filename) { - uint32_t index = 0; - uint32_t instance = BACNET_MAX_INSTANCE + 1; + uint32_t index = 0; + uint32_t instance = BACNET_MAX_INSTANCE + 1; - // linear search for filename match - while (BACnet_File_Listing[index].filename) - { - if (strcmp(BACnet_File_Listing[index].filename,filename) == 0) - { - instance = BACnet_File_Listing[index].instance; - break; + // linear search for filename match + while (BACnet_File_Listing[index].filename) { + if (strcmp(BACnet_File_Listing[index].filename, filename) == 0) { + instance = BACnet_File_Listing[index].instance; + break; + } + index++; } - index++; - } - return instance; + return instance; } #if TSM_ENABLED @@ -248,102 +223,80 @@ uint32_t bacfile_instance(char *filename) // Another way would be to store the // invokeID and file instance in a list or table // when the request was sent -uint32_t bacfile_instance_from_tsm( - uint8_t invokeID) +uint32_t bacfile_instance_from_tsm(uint8_t invokeID) { - BACNET_NPDU_DATA npdu_data = {0}; // dummy for getting npdu length - BACNET_CONFIRMED_SERVICE_DATA service_data = {0}; - uint8_t service_choice = 0; - uint8_t *service_request = NULL; - uint16_t service_request_len = 0; - BACNET_ADDRESS dest; // where the original packet was destined - uint8_t pdu[MAX_PDU] = {0}; // original sent packet - uint16_t pdu_len = 0; // original packet length - uint16_t len = 0; // apdu header length - BACNET_ATOMIC_READ_FILE_DATA data = {0}; - uint32_t object_instance = BACNET_MAX_INSTANCE + 1; // return value - bool found = false; - int apdu_offset = 0; - - found = tsm_get_transaction_pdu( - invokeID, - &dest, - &pdu[0], - &pdu_len); - if (found) - { - apdu_offset = npdu_decode( - &pdu[0], // data to decode - NULL, // destination address - get the DNET/DLEN/DADR if in there - NULL, // source address - get the SNET/SLEN/SADR if in there - &npdu_data); // amount of data to decode - if (!npdu_data.network_layer_message && - ((pdu[apdu_offset] & 0xF0) == PDU_TYPE_CONFIRMED_SERVICE_REQUEST)) - { - len = apdu_decode_confirmed_service_request( - &pdu[apdu_offset], // APDU data - pdu_len - apdu_offset, - &service_data, - &service_choice, - &service_request, - &service_request_len); - if (service_choice == SERVICE_CONFIRMED_ATOMIC_READ_FILE) - { - len = arf_decode_service_request( - service_request, - service_request_len, - &data); - if (len > 0) - { - if (data.object_type == OBJECT_FILE) - object_instance = data.object_instance; + BACNET_NPDU_DATA npdu_data = { 0 }; // dummy for getting npdu length + BACNET_CONFIRMED_SERVICE_DATA service_data = { 0 }; + uint8_t service_choice = 0; + uint8_t *service_request = NULL; + uint16_t service_request_len = 0; + BACNET_ADDRESS dest; // where the original packet was destined + uint8_t pdu[MAX_PDU] = { 0 }; // original sent packet + uint16_t pdu_len = 0; // original packet length + uint16_t len = 0; // apdu header length + BACNET_ATOMIC_READ_FILE_DATA data = { 0 }; + uint32_t object_instance = BACNET_MAX_INSTANCE + 1; // return value + bool found = false; + int apdu_offset = 0; + + found = tsm_get_transaction_pdu(invokeID, &dest, &pdu[0], &pdu_len); + if (found) { + apdu_offset = npdu_decode(&pdu[0], // data to decode + NULL, // destination address - get the DNET/DLEN/DADR if in there + NULL, // source address - get the SNET/SLEN/SADR if in there + &npdu_data); // amount of data to decode + if (!npdu_data.network_layer_message && + ((pdu[apdu_offset] & 0xF0) == + PDU_TYPE_CONFIRMED_SERVICE_REQUEST)) { + len = apdu_decode_confirmed_service_request(&pdu[apdu_offset], // APDU data + pdu_len - apdu_offset, + &service_data, + &service_choice, &service_request, &service_request_len); + if (service_choice == SERVICE_CONFIRMED_ATOMIC_READ_FILE) { + len = arf_decode_service_request(service_request, + service_request_len, &data); + if (len > 0) { + if (data.object_type == OBJECT_FILE) + object_instance = data.object_instance; + } + } } - } } - } - - return object_instance; + + return object_instance; } #endif -bool bacfile_read_data(BACNET_ATOMIC_READ_FILE_DATA *data) +bool bacfile_read_data(BACNET_ATOMIC_READ_FILE_DATA * data) { - char *pFilename = NULL; - bool found = false; - FILE *pFile = NULL; - size_t len = 0; - - pFilename = bacfile_name(data->object_instance); - if (pFilename) - { - found = true; - pFile = fopen(pFilename,"rb"); - if (pFile) - { - (void)fseek(pFile, - data->type.stream.fileStartPosition, - SEEK_SET); - len = fread(octetstring_value(&data->fileData), 1, - data->type.stream.requestedOctetCount, pFile); - if (len < data->type.stream.requestedOctetCount) - data->endOfFile = true; - else - data->endOfFile = false; - octetstring_truncate(&data->fileData,len); - fclose(pFile); - } - else - { - octetstring_truncate(&data->fileData,0); - data->endOfFile = true; - } - } - else - { - octetstring_truncate(&data->fileData,0); - data->endOfFile = true; - } + char *pFilename = NULL; + bool found = false; + FILE *pFile = NULL; + size_t len = 0; - return found; + pFilename = bacfile_name(data->object_instance); + if (pFilename) { + found = true; + pFile = fopen(pFilename, "rb"); + if (pFile) { + (void) fseek(pFile, + data->type.stream.fileStartPosition, SEEK_SET); + len = fread(octetstring_value(&data->fileData), 1, + data->type.stream.requestedOctetCount, pFile); + if (len < data->type.stream.requestedOctetCount) + data->endOfFile = true; + else + data->endOfFile = false; + octetstring_truncate(&data->fileData, len); + fclose(pFile); + } else { + octetstring_truncate(&data->fileData, 0); + data->endOfFile = true; + } + } else { + octetstring_truncate(&data->fileData, 0); + data->endOfFile = true; + } + + return found; } - diff --git a/bacnet-stack/demo/object/bacfile.h b/bacnet-stack/demo/object/bacfile.h index e046caed..b08ecb53 100644 --- a/bacnet-stack/demo/object/bacfile.h +++ b/bacnet-stack/demo/object/bacfile.h @@ -43,37 +43,33 @@ #ifdef __cplusplus extern "C" { -#endif /* __cplusplus */ +#endif /* __cplusplus */ -char *bacfile_name(uint32_t instance); -bool bacfile_valid_instance(uint32_t object_instance); -uint32_t bacfile_count(void); -uint32_t bacfile_index_to_instance(unsigned find_index); -uint32_t bacfile_instance(char *filename); + char *bacfile_name(uint32_t instance); + bool bacfile_valid_instance(uint32_t object_instance); + uint32_t bacfile_count(void); + uint32_t bacfile_index_to_instance(unsigned find_index); + uint32_t bacfile_instance(char *filename); #if TSM_ENABLED // this is one way to match up the invoke ID with // the file ID from the AtomicReadFile request. // Another way would be to store the // invokeID and file instance in a list or table // when the request was sent -uint32_t bacfile_instance_from_tsm( - uint8_t invokeID); + uint32_t bacfile_instance_from_tsm(uint8_t invokeID); #endif // AtomicReadFile ACK helper -bool bacfile_read_data(BACNET_ATOMIC_READ_FILE_DATA *data); + bool bacfile_read_data(BACNET_ATOMIC_READ_FILE_DATA * data); // handling for read property service -int bacfile_encode_property_apdu( - uint8_t *apdu, - uint32_t object_instance, - BACNET_PROPERTY_ID property, - int32_t array_index, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code); + int bacfile_encode_property_apdu(uint8_t * apdu, + uint32_t object_instance, + BACNET_PROPERTY_ID property, + int32_t array_index, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code); #ifdef __cplusplus } -#endif /* __cplusplus */ - +#endif /* __cplusplus */ #endif diff --git a/bacnet-stack/demo/object/device.c b/bacnet-stack/demo/object/device.c index 4a783112..2864f679 100644 --- a/bacnet-stack/demo/object/device.c +++ b/bacnet-stack/demo/object/device.c @@ -25,18 +25,18 @@ #include #include -#include /* for memmove*/ +#include /* for memmove */ #include "bacdef.h" #include "bacdcode.h" #include "bacenum.h" -#include "config.h" /* the custom stuff */ +#include "config.h" /* the custom stuff */ #include "apdu.h" -#include "ai.h" /* object list dependency */ -#include "ao.h" /* object list dependency */ -#include "wp.h" /* write property handling */ -#include "device.h" /* me */ +#include "ai.h" /* object list dependency */ +#include "ao.h" /* object list dependency */ +#include "wp.h" /* write property handling */ +#include "device.h" /* me */ #if BACFILE -#include "bacfile.h" /* object list dependency */ +#include "bacfile.h" /* object list dependency */ #endif /* note: you really only need to define variables for @@ -90,455 +90,431 @@ static uint8_t Database_Revision = 0; /* methods to manipulate the data */ uint32_t Device_Object_Instance_Number(void) { - return Object_Instance_Number; + return Object_Instance_Number; } bool Device_Set_Object_Instance_Number(uint32_t object_id) { - bool status = true; /* return value */ + bool status = true; /* return value */ - if (object_id <= BACNET_MAX_INSTANCE) - Object_Instance_Number = object_id; - else - status = false; + if (object_id <= BACNET_MAX_INSTANCE) + Object_Instance_Number = object_id; + else + status = false; - return status; + return status; } bool Device_Valid_Object_Instance_Number(uint32_t object_id) { - // BACnet allows for a wildcard instance number - return ((Object_Instance_Number == object_id) || - (object_id == BACNET_MAX_INSTANCE)); + // BACnet allows for a wildcard instance number + return ((Object_Instance_Number == object_id) || + (object_id == BACNET_MAX_INSTANCE)); } const char *Device_Object_Name(void) { - return Object_Name; + return Object_Name; } bool Device_Set_Object_Name(const char *name, size_t length) { - bool status = false; /*return value*/ + bool status = false; /*return value */ - if (length < sizeof(Object_Name)) - { - memmove(Object_Name,name,length); - Object_Name[length] = 0; - status = true; - } + if (length < sizeof(Object_Name)) { + memmove(Object_Name, name, length); + Object_Name[length] = 0; + status = true; + } - return status; + return status; } BACNET_DEVICE_STATUS Device_System_Status(void) { - return System_Status; + return System_Status; } void Device_Set_System_Status(BACNET_DEVICE_STATUS status) { - // FIXME: bounds check? - System_Status = status; + // FIXME: bounds check? + System_Status = status; } const char *Device_Vendor_Name(void) { - return Vendor_Name; + return Vendor_Name; } bool Device_Set_Vendor_Name(const char *name, size_t length) { - bool status = false; /*return value*/ + bool status = false; /*return value */ - if (length < sizeof(Vendor_Name)) - { - memmove(Vendor_Name,name,length); - Vendor_Name[length] = 0; - status = true; - } + if (length < sizeof(Vendor_Name)) { + memmove(Vendor_Name, name, length); + Vendor_Name[length] = 0; + status = true; + } - return status; + return status; } uint16_t Device_Vendor_Identifier(void) { - return Vendor_Identifier; + return Vendor_Identifier; } void Device_Set_Vendor_Identifier(uint16_t vendor_id) { - Vendor_Identifier = vendor_id; + Vendor_Identifier = vendor_id; } const char *Device_Model_Name(void) { - return Model_Name; + return Model_Name; } bool Device_Set_Model_Name(const char *name, size_t length) { - bool status = false; /*return value*/ + bool status = false; /*return value */ - if (length < sizeof(Model_Name)) - { - memmove(Model_Name,name,length); - Model_Name[length] = 0; - status = true; - } + if (length < sizeof(Model_Name)) { + memmove(Model_Name, name, length); + Model_Name[length] = 0; + status = true; + } - return status; + return status; } const char *Device_Firmware_Revision(void) { - return Firmware_Revision; + return Firmware_Revision; } bool Device_Set_Firmware_Revision(const char *name, size_t length) { - bool status = false; /*return value*/ + bool status = false; /*return value */ - if (length < sizeof(Firmware_Revision)) - { - memmove(Firmware_Revision,name,length); - Firmware_Revision[length] = 0; - status = true; - } + if (length < sizeof(Firmware_Revision)) { + memmove(Firmware_Revision, name, length); + Firmware_Revision[length] = 0; + status = true; + } - return status; + return status; } const char *Device_Application_Software_Version(void) { - return Application_Software_Version; + return Application_Software_Version; } -bool Device_Set_Application_Software_Version(const char *name, size_t length) +bool Device_Set_Application_Software_Version(const char *name, + size_t length) { - bool status = false; /*return value*/ + bool status = false; /*return value */ - if (length < sizeof(Application_Software_Version)) - { - memmove(Application_Software_Version,name,length); - Application_Software_Version[length] = 0; - status = true; - } + if (length < sizeof(Application_Software_Version)) { + memmove(Application_Software_Version, name, length); + Application_Software_Version[length] = 0; + status = true; + } - return status; + return status; } const char *Device_Description(void) { - return Description; + return Description; } bool Device_Set_Description(const char *name, size_t length) { - bool status = false; /*return value*/ + bool status = false; /*return value */ - if (length < sizeof(Description)) - { - memmove(Description,name,length); - Description[length] = 0; - status = true; - } + if (length < sizeof(Description)) { + memmove(Description, name, length); + Description[length] = 0; + status = true; + } - return status; + return status; } const char *Device_Location(void) { - return Location; + return Location; } bool Device_Set_Location(const char *name, size_t length) { - bool status = false; /*return value*/ + bool status = false; /*return value */ - if (length < sizeof(Location)) - { - memmove(Location,name,length); - Location[length] = 0; - status = true; - } + if (length < sizeof(Location)) { + memmove(Location, name, length); + Location[length] = 0; + status = true; + } - return status; + return status; } uint8_t Device_Protocol_Version(void) { - return 1; + return 1; } uint8_t Device_Protocol_Revision(void) { - return 4; + return 4; } uint16_t Device_Max_APDU_Length_Accepted(void) { - return MAX_APDU; + return MAX_APDU; } BACNET_SEGMENTATION Device_Segmentation_Supported(void) { - return SEGMENTATION_NONE; + return SEGMENTATION_NONE; } uint16_t Device_APDU_Timeout(void) { - return APDU_Timeout; + return APDU_Timeout; } // in milliseconds void Device_Set_APDU_Timeout(uint16_t timeout) { - APDU_Timeout = timeout; + APDU_Timeout = timeout; } uint8_t Device_Number_Of_APDU_Retries(void) { - return Number_Of_APDU_Retries; + return Number_Of_APDU_Retries; } void Device_Set_Number_Of_APDU_Retries(uint8_t retries) { - Number_Of_APDU_Retries = retries; + Number_Of_APDU_Retries = retries; } uint8_t Device_Database_Revision(void) { - return Database_Revision; + return Database_Revision; } void Device_Set_Database_Revision(uint8_t revision) { - Database_Revision = revision; + Database_Revision = revision; } // Since many network clients depend on the object list // for discovery, it must be consistent! unsigned Device_Object_List_Count(void) { - unsigned count = 1; + unsigned count = 1; - count += Analog_Input_Count(); - count += Analog_Output_Count(); - #if BACFILE - count += bacfile_count(); - #endif + count += Analog_Input_Count(); + count += Analog_Output_Count(); +#if BACFILE + count += bacfile_count(); +#endif - return count; + return count; } bool Device_Object_List_Identifier(unsigned array_index, - int *object_type, - uint32_t *instance) + int *object_type, uint32_t * instance) { - bool status = false; - unsigned object_index = 0; + bool status = false; + unsigned object_index = 0; - if (array_index == 1) - { - *object_type = OBJECT_DEVICE; - *instance = Object_Instance_Number; - status = true; - } - - if (!status) - { - // array index starts at 1, and 1 for the device object - object_index = array_index - 2; - if (object_index < Analog_Input_Count()) - { - *object_type = OBJECT_ANALOG_INPUT; - *instance = Analog_Input_Index_To_Instance(object_index); - status = true; + if (array_index == 1) { + *object_type = OBJECT_DEVICE; + *instance = Object_Instance_Number; + status = true; } - } - if (!status) - { - object_index -= Analog_Input_Count(); - if (object_index < Analog_Output_Count()) - { - *object_type = OBJECT_ANALOG_OUTPUT; - *instance = Analog_Output_Index_To_Instance(object_index); - status = true; - } - } - #if BACFILE - if (!status) - { - object_index -= Analog_Output_Count(); - if (object_index < bacfile_count()) - { - *object_type = OBJECT_FILE; - *instance = bacfile_index_to_instance(object_index); - status = true; + if (!status) { + // array index starts at 1, and 1 for the device object + object_index = array_index - 2; + if (object_index < Analog_Input_Count()) { + *object_type = OBJECT_ANALOG_INPUT; + *instance = Analog_Input_Index_To_Instance(object_index); + status = true; + } } - } - #endif + if (!status) { + object_index -= Analog_Input_Count(); + if (object_index < Analog_Output_Count()) { + *object_type = OBJECT_ANALOG_OUTPUT; + *instance = Analog_Output_Index_To_Instance(object_index); + status = true; + } + } +#if BACFILE + if (!status) { + object_index -= Analog_Output_Count(); + if (object_index < bacfile_count()) { + *object_type = OBJECT_FILE; + *instance = bacfile_index_to_instance(object_index); + status = true; + } + } +#endif - return status; + return status; } -bool Device_Valid_Object_Name( - const char *object_name, - int *object_type, - uint32_t *object_instance) +bool Device_Valid_Object_Name(const char *object_name, + int *object_type, uint32_t * object_instance) { - bool found = false; - int type = 0; - uint32_t instance; - unsigned max_objects = 0, i = 0; - bool check_id = false; - char *name = NULL; - - max_objects = Device_Object_List_Count(); - for (i = 0; i < max_objects; i++) - { - check_id = Device_Object_List_Identifier(i, &type, &instance); - if (check_id) - { - name = Device_Valid_Object_Id(type,instance); - if (strcmp(name,object_name) == 0) - { - found = true; - if (object_type) - *object_type = type; - if (object_instance) - *object_instance = instance; - break; - } + bool found = false; + int type = 0; + uint32_t instance; + unsigned max_objects = 0, i = 0; + bool check_id = false; + char *name = NULL; + + max_objects = Device_Object_List_Count(); + for (i = 0; i < max_objects; i++) { + check_id = Device_Object_List_Identifier(i, &type, &instance); + if (check_id) { + name = Device_Valid_Object_Id(type, instance); + if (strcmp(name, object_name) == 0) { + found = true; + if (object_type) + *object_type = type; + if (object_instance) + *object_instance = instance; + break; + } + } } - } - - return found; + + return found; } /* returns the name or NULL if not found */ -char *Device_Valid_Object_Id( - int object_type, - uint32_t object_instance) +char *Device_Valid_Object_Id(int object_type, uint32_t object_instance) { - char *name = NULL; /* return value */ + char *name = NULL; /* return value */ - switch (object_type) - { + switch (object_type) { case OBJECT_ANALOG_INPUT: - name = Analog_Input_Name(object_instance); - break; + name = Analog_Input_Name(object_instance); + break; case OBJECT_ANALOG_OUTPUT: - name = Analog_Output_Name(object_instance); - break; + name = Analog_Output_Name(object_instance); + break; #if BACFILE case OBJECT_FILE: - name = bacfile_name(object_instance); - break; + name = bacfile_name(object_instance); + break; #endif case OBJECT_DEVICE: - if (object_instance == Object_Instance_Number) - name = Object_Name; - break; + if (object_instance == Object_Instance_Number) + name = Object_Name; + break; default: - break; - } - - return name; + break; + } + + return name; } // return the length of the apdu encoded or -1 for error -int Device_Encode_Property_APDU( - uint8_t *apdu, - BACNET_PROPERTY_ID property, - int32_t array_index, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code) +int Device_Encode_Property_APDU(uint8_t * apdu, + BACNET_PROPERTY_ID property, + int32_t array_index, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code) { - int apdu_len = 0; // return value - int len = 0; // apdu len intermediate value - BACNET_BIT_STRING bit_string; - BACNET_CHARACTER_STRING char_string; - unsigned i = 0; - int object_type = 0; - uint32_t instance = 0; - unsigned count = 0; + int apdu_len = 0; // return value + int len = 0; // apdu len intermediate value + BACNET_BIT_STRING bit_string; + BACNET_CHARACTER_STRING char_string; + unsigned i = 0; + int object_type = 0; + uint32_t instance = 0; + unsigned count = 0; - switch (property) - { + switch (property) { case PROP_OBJECT_IDENTIFIER: - apdu_len = encode_tagged_object_id(&apdu[0], OBJECT_DEVICE, - Object_Instance_Number); - break; - case PROP_OBJECT_NAME: - characterstring_init_ansi(&char_string, Object_Name); - apdu_len = encode_tagged_character_string(&apdu[0], &char_string); - break; - case PROP_OBJECT_TYPE: - apdu_len = encode_tagged_enumerated(&apdu[0], OBJECT_DEVICE); - break; - case PROP_DESCRIPTION: - characterstring_init_ansi(&char_string, Description); - apdu_len = encode_tagged_character_string(&apdu[0], &char_string); - break; - case PROP_SYSTEM_STATUS: - apdu_len = encode_tagged_enumerated(&apdu[0], System_Status); - break; - case PROP_VENDOR_NAME: - characterstring_init_ansi(&char_string, Vendor_Name); - apdu_len = encode_tagged_character_string(&apdu[0], &char_string); - break; - case PROP_VENDOR_IDENTIFIER: - apdu_len = encode_tagged_unsigned(&apdu[0], Vendor_Identifier); - break; - case PROP_MODEL_NAME: - characterstring_init_ansi(&char_string, Model_Name); - apdu_len = encode_tagged_character_string(&apdu[0], &char_string); - break; - case PROP_FIRMWARE_REVISION: - characterstring_init_ansi(&char_string, Firmware_Revision); - apdu_len = encode_tagged_character_string(&apdu[0], &char_string); - break; - case PROP_APPLICATION_SOFTWARE_VERSION: - characterstring_init_ansi(&char_string, Application_Software_Version); - apdu_len = encode_tagged_character_string(&apdu[0], &char_string); - break; - // if you support time - //case PROP_LOCAL_TIME: - //t = time(NULL); - //my_tm = localtime(&t); - //apdu_len = - // encode_tagged_time(&apdu[0], my_tm->tm_hour, my_tm->tm_min, - // my_tm->tm_sec, 0); - //break; - // if you support date - //case PROP_LOCAL_DATE: - //t = time(NULL); - //my_tm = localtime(&t); - // month 1=Jan - // day = day of month - // wday 1=Monday...7=Sunday - //apdu_len = encode_tagged_date(&apdu[0], - // my_tm->tm_year+1900, - // my_tm->tm_mon + 1, - // my_tm->tm_mday, ((my_tm->tm_wday == 0) ? 7 : my_tm->tm_wday)); - //break; - case PROP_PROTOCOL_VERSION: - apdu_len = encode_tagged_unsigned(&apdu[0], Device_Protocol_Version()); + apdu_len = encode_tagged_object_id(&apdu[0], OBJECT_DEVICE, + Object_Instance_Number); break; - // BACnet Legacy Support + case PROP_OBJECT_NAME: + characterstring_init_ansi(&char_string, Object_Name); + apdu_len = encode_tagged_character_string(&apdu[0], &char_string); + break; + case PROP_OBJECT_TYPE: + apdu_len = encode_tagged_enumerated(&apdu[0], OBJECT_DEVICE); + break; + case PROP_DESCRIPTION: + characterstring_init_ansi(&char_string, Description); + apdu_len = encode_tagged_character_string(&apdu[0], &char_string); + break; + case PROP_SYSTEM_STATUS: + apdu_len = encode_tagged_enumerated(&apdu[0], System_Status); + break; + case PROP_VENDOR_NAME: + characterstring_init_ansi(&char_string, Vendor_Name); + apdu_len = encode_tagged_character_string(&apdu[0], &char_string); + break; + case PROP_VENDOR_IDENTIFIER: + apdu_len = encode_tagged_unsigned(&apdu[0], Vendor_Identifier); + break; + case PROP_MODEL_NAME: + characterstring_init_ansi(&char_string, Model_Name); + apdu_len = encode_tagged_character_string(&apdu[0], &char_string); + break; + case PROP_FIRMWARE_REVISION: + characterstring_init_ansi(&char_string, Firmware_Revision); + apdu_len = encode_tagged_character_string(&apdu[0], &char_string); + break; + case PROP_APPLICATION_SOFTWARE_VERSION: + characterstring_init_ansi(&char_string, + Application_Software_Version); + apdu_len = encode_tagged_character_string(&apdu[0], &char_string); + break; + // if you support time + //case PROP_LOCAL_TIME: + //t = time(NULL); + //my_tm = localtime(&t); + //apdu_len = + // encode_tagged_time(&apdu[0], my_tm->tm_hour, my_tm->tm_min, + // my_tm->tm_sec, 0); + //break; + // if you support date + //case PROP_LOCAL_DATE: + //t = time(NULL); + //my_tm = localtime(&t); + // month 1=Jan + // day = day of month + // wday 1=Monday...7=Sunday + //apdu_len = encode_tagged_date(&apdu[0], + // my_tm->tm_year+1900, + // my_tm->tm_mon + 1, + // my_tm->tm_mday, ((my_tm->tm_wday == 0) ? 7 : my_tm->tm_wday)); + //break; + case PROP_PROTOCOL_VERSION: + apdu_len = + encode_tagged_unsigned(&apdu[0], Device_Protocol_Version()); + break; + // BACnet Legacy Support case PROP_PROTOCOL_CONFORMANCE_CLASS: apdu_len = encode_tagged_unsigned(&apdu[0], 1); break; case PROP_PROTOCOL_SERVICES_SUPPORTED: /* Note: list of services that are executed, not initiated. */ bitstring_init(&bit_string); - for (i = 0; i < MAX_BACNET_SERVICES_SUPPORTED; i++) - { - /* automatic lookup based on handlers set */ - bitstring_set_bit(&bit_string, (uint8_t)i, apdu_service_supported(i)); + for (i = 0; i < MAX_BACNET_SERVICES_SUPPORTED; i++) { + /* automatic lookup based on handlers set */ + bitstring_set_bit(&bit_string, (uint8_t) i, + apdu_service_supported(i)); } apdu_len = encode_tagged_bitstring(&apdu[0], &bit_string); break; @@ -546,232 +522,205 @@ int Device_Encode_Property_APDU( /* Note: this is the list of objects that can be in this device, not a list of objects that this device can access */ bitstring_init(&bit_string); - for (i = 0; i < MAX_ASHRAE_OBJECT_TYPE; i++) - { - // initialize all the object types to not-supported - bitstring_set_bit(&bit_string, (uint8_t)i, false); + for (i = 0; i < MAX_ASHRAE_OBJECT_TYPE; i++) { + // initialize all the object types to not-supported + bitstring_set_bit(&bit_string, (uint8_t) i, false); } /* FIXME: indicate the objects that YOU support */ bitstring_set_bit(&bit_string, OBJECT_DEVICE, true); bitstring_set_bit(&bit_string, OBJECT_ANALOG_INPUT, true); bitstring_set_bit(&bit_string, OBJECT_ANALOG_OUTPUT, true); - #if BACFILE +#if BACFILE bitstring_set_bit(&bit_string, OBJECT_FILE, true); - #endif +#endif apdu_len = encode_tagged_bitstring(&apdu[0], &bit_string); break; case PROP_OBJECT_LIST: - count = Device_Object_List_Count(); - // Array element zero is the number of objects in the list - if (array_index == BACNET_ARRAY_LENGTH_INDEX) - apdu_len = encode_tagged_unsigned(&apdu[0], count); - // if no index was specified, then try to encode the entire list - // into one packet. Note that more than likely you will have - // to return an error if the number of encoded objects exceeds - // your maximum APDU size. - else if (array_index == BACNET_ARRAY_ALL) - { - for (i = 1; i <= count; i++) - { - if (Device_Object_List_Identifier(i,&object_type,&instance)) - { - len = encode_tagged_object_id(&apdu[apdu_len], object_type, - instance); - apdu_len += len; - // assume next one is the same size as this one - // can we all fit into the APDU? - if ((apdu_len + len) >= MAX_APDU) - { - *error_class = ERROR_CLASS_SERVICES; - *error_code = ERROR_CODE_NO_SPACE_FOR_OBJECT; - apdu_len = -1; - break; + count = Device_Object_List_Count(); + // Array element zero is the number of objects in the list + if (array_index == BACNET_ARRAY_LENGTH_INDEX) + apdu_len = encode_tagged_unsigned(&apdu[0], count); + // if no index was specified, then try to encode the entire list + // into one packet. Note that more than likely you will have + // to return an error if the number of encoded objects exceeds + // your maximum APDU size. + else if (array_index == BACNET_ARRAY_ALL) { + for (i = 1; i <= count; i++) { + if (Device_Object_List_Identifier(i, &object_type, + &instance)) { + len = + encode_tagged_object_id(&apdu[apdu_len], + object_type, instance); + apdu_len += len; + // assume next one is the same size as this one + // can we all fit into the APDU? + if ((apdu_len + len) >= MAX_APDU) { + *error_class = ERROR_CLASS_SERVICES; + *error_code = ERROR_CODE_NO_SPACE_FOR_OBJECT; + apdu_len = -1; + break; + } + } else { + // error: internal error? + *error_class = ERROR_CLASS_SERVICES; + *error_code = ERROR_CODE_OTHER; + apdu_len = -1; + break; + } + } + } else { + if (Device_Object_List_Identifier(array_index, &object_type, + &instance)) + apdu_len = + encode_tagged_object_id(&apdu[0], object_type, + instance); + else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_INVALID_ARRAY_INDEX; + apdu_len = -1; } - } - else - { - // error: internal error? - *error_class = ERROR_CLASS_SERVICES; - *error_code = ERROR_CODE_OTHER; - apdu_len = -1; - break; - } } - } - else - { - if (Device_Object_List_Identifier(array_index,&object_type,&instance)) - apdu_len = encode_tagged_object_id(&apdu[0], object_type, instance); - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_INVALID_ARRAY_INDEX; - apdu_len = -1; - } - } - break; + break; case PROP_MAX_APDU_LENGTH_ACCEPTED: - apdu_len = encode_tagged_unsigned(&apdu[0], - Device_Max_APDU_Length_Accepted()); - break; + apdu_len = encode_tagged_unsigned(&apdu[0], + Device_Max_APDU_Length_Accepted()); + break; case PROP_SEGMENTATION_SUPPORTED: - apdu_len = encode_tagged_enumerated(&apdu[0], - Device_Segmentation_Supported()); - break; + apdu_len = encode_tagged_enumerated(&apdu[0], + Device_Segmentation_Supported()); + break; case PROP_APDU_TIMEOUT: - apdu_len = encode_tagged_unsigned(&apdu[0], APDU_Timeout); - break; + apdu_len = encode_tagged_unsigned(&apdu[0], APDU_Timeout); + break; case PROP_NUMBER_OF_APDU_RETRIES: - apdu_len = encode_tagged_unsigned(&apdu[0], Number_Of_APDU_Retries); - break; + apdu_len = + encode_tagged_unsigned(&apdu[0], Number_Of_APDU_Retries); + break; case PROP_DEVICE_ADDRESS_BINDING: - /* encode the list here, if it exists */ - break; + /* encode the list here, if it exists */ + break; default: - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_UNKNOWN_PROPERTY; - apdu_len = -1; - break; - } + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_UNKNOWN_PROPERTY; + apdu_len = -1; + break; + } - return apdu_len; + return apdu_len; } // we can send an I-Am when our device ID changes extern bool I_Am_Request; // returns true if successful -bool Device_Write_Property( - BACNET_WRITE_PROPERTY_DATA *wp_data, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code) +bool Device_Write_Property(BACNET_WRITE_PROPERTY_DATA * wp_data, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code) { - bool status = false; // return value + bool status = false; // return value - if (!Device_Valid_Object_Instance_Number(wp_data->object_instance)) - { - *error_class = ERROR_CLASS_OBJECT; - *error_code = ERROR_CODE_UNKNOWN_OBJECT; - return false; - } - - // decode the some of the request - switch (wp_data->object_property) - { + if (!Device_Valid_Object_Instance_Number(wp_data->object_instance)) { + *error_class = ERROR_CLASS_OBJECT; + *error_code = ERROR_CODE_UNKNOWN_OBJECT; + return false; + } + // decode the some of the request + switch (wp_data->object_property) { case PROP_OBJECT_IDENTIFIER: - if (wp_data->value.tag == BACNET_APPLICATION_TAG_OBJECT_ID) - { - if ((wp_data->value.type.Object_Id.type == OBJECT_DEVICE) && - (Device_Set_Object_Instance_Number( - wp_data->value.type.Object_Id.instance))) - { - I_Am_Request = true; - status = true; + if (wp_data->value.tag == BACNET_APPLICATION_TAG_OBJECT_ID) { + if ((wp_data->value.type.Object_Id.type == OBJECT_DEVICE) && + (Device_Set_Object_Instance_Number(wp_data->value.type. + Object_Id.instance))) { + I_Am_Request = true; + status = true; + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_VALUE_OUT_OF_RANGE; + } + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_INVALID_DATA_TYPE; } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_VALUE_OUT_OF_RANGE; - } - } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_INVALID_DATA_TYPE; - } - break; + break; case PROP_NUMBER_OF_APDU_RETRIES: - if (wp_data->value.tag == BACNET_APPLICATION_TAG_UNSIGNED_INT) - { - /* FIXME: bounds check? */ - Device_Set_Number_Of_APDU_Retries((uint8_t)wp_data->value.type.Unsigned_Int); - status = true; - } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_INVALID_DATA_TYPE; - } - break; + if (wp_data->value.tag == BACNET_APPLICATION_TAG_UNSIGNED_INT) { + /* FIXME: bounds check? */ + Device_Set_Number_Of_APDU_Retries((uint8_t) wp_data->value. + type.Unsigned_Int); + status = true; + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_INVALID_DATA_TYPE; + } + break; case PROP_APDU_TIMEOUT: - if (wp_data->value.tag == BACNET_APPLICATION_TAG_UNSIGNED_INT) - { - /* FIXME: bounds check? */ - Device_Set_APDU_Timeout((uint16_t)wp_data->value.type.Unsigned_Int); - status = true; - } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_INVALID_DATA_TYPE; - } - break; + if (wp_data->value.tag == BACNET_APPLICATION_TAG_UNSIGNED_INT) { + /* FIXME: bounds check? */ + Device_Set_APDU_Timeout((uint16_t) wp_data->value.type. + Unsigned_Int); + status = true; + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_INVALID_DATA_TYPE; + } + break; case PROP_VENDOR_IDENTIFIER: - if (wp_data->value.tag == BACNET_APPLICATION_TAG_UNSIGNED_INT) - { - /* FIXME: bounds check? */ - Device_Set_Vendor_Identifier((uint16_t)wp_data->value.type.Unsigned_Int); - status = true; - } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_INVALID_DATA_TYPE; - } - break; + if (wp_data->value.tag == BACNET_APPLICATION_TAG_UNSIGNED_INT) { + /* FIXME: bounds check? */ + Device_Set_Vendor_Identifier((uint16_t) wp_data->value.type. + Unsigned_Int); + status = true; + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_INVALID_DATA_TYPE; + } + break; case PROP_SYSTEM_STATUS: - if (wp_data->value.tag == BACNET_APPLICATION_TAG_ENUMERATED) - { - Device_Set_System_Status(wp_data->value.type.Enumerated); - status = true; - } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_INVALID_DATA_TYPE; - } - break; + if (wp_data->value.tag == BACNET_APPLICATION_TAG_ENUMERATED) { + Device_Set_System_Status(wp_data->value.type.Enumerated); + status = true; + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_INVALID_DATA_TYPE; + } + break; case PROP_OBJECT_NAME: - if (wp_data->value.tag == BACNET_APPLICATION_TAG_CHARACTER_STRING) - { - uint8_t encoding; - encoding = characterstring_encoding(&wp_data->value.type.Character_String); - if (encoding == CHARACTER_ANSI_X34) - { - status = Device_Set_Object_Name( - characterstring_value(&wp_data->value.type.Character_String), - characterstring_length(&wp_data->value.type.Character_String)); - if (!status) - { + if (wp_data->value.tag == BACNET_APPLICATION_TAG_CHARACTER_STRING) { + uint8_t encoding; + encoding = + characterstring_encoding(&wp_data->value.type. + Character_String); + if (encoding == CHARACTER_ANSI_X34) { + status = + Device_Set_Object_Name(characterstring_value(&wp_data-> + value.type.Character_String), + characterstring_length(&wp_data->value.type. + Character_String)); + if (!status) { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_NO_SPACE_TO_WRITE_PROPERTY; + } + } else { + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_CHARACTER_SET_NOT_SUPPORTED; + } + } else { *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_NO_SPACE_TO_WRITE_PROPERTY; - } + *error_code = ERROR_CODE_INVALID_DATA_TYPE; } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_CHARACTER_SET_NOT_SUPPORTED; - } - } - else - { - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_INVALID_DATA_TYPE; - } - break; + break; default: - *error_class = ERROR_CLASS_PROPERTY; - *error_code = ERROR_CODE_WRITE_ACCESS_DENIED; - break; - } + *error_class = ERROR_CLASS_PROPERTY; + *error_code = ERROR_CODE_WRITE_ACCESS_DENIED; + break; + } - return status; + return status; } #ifdef TEST @@ -781,68 +730,70 @@ bool Device_Write_Property( void testDevice(Test * pTest) { - bool status = false; - const char *name = "Patricia"; + bool status = false; + const char *name = "Patricia"; - status = Device_Set_Object_Instance_Number(0); - ct_test(pTest, Device_Object_Instance_Number() == 0); - ct_test(pTest, status == true); - status = Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); - ct_test(pTest, Device_Object_Instance_Number() == BACNET_MAX_INSTANCE); - ct_test(pTest, status == true); - status = Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE/2); - ct_test(pTest, Device_Object_Instance_Number() == (BACNET_MAX_INSTANCE/2)); - ct_test(pTest, status == true); - status = Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE+1); - ct_test(pTest, Device_Object_Instance_Number() != (BACNET_MAX_INSTANCE+1)); - ct_test(pTest, status == false); + status = Device_Set_Object_Instance_Number(0); + ct_test(pTest, Device_Object_Instance_Number() == 0); + ct_test(pTest, status == true); + status = Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); + ct_test(pTest, Device_Object_Instance_Number() == BACNET_MAX_INSTANCE); + ct_test(pTest, status == true); + status = Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE / 2); + ct_test(pTest, + Device_Object_Instance_Number() == (BACNET_MAX_INSTANCE / 2)); + ct_test(pTest, status == true); + status = Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE + 1); + ct_test(pTest, + Device_Object_Instance_Number() != (BACNET_MAX_INSTANCE + 1)); + ct_test(pTest, status == false); - Device_Set_System_Status(STATUS_NON_OPERATIONAL); - ct_test(pTest, Device_System_Status() == STATUS_NON_OPERATIONAL); + Device_Set_System_Status(STATUS_NON_OPERATIONAL); + ct_test(pTest, Device_System_Status() == STATUS_NON_OPERATIONAL); - Device_Set_Vendor_Name(name,strlen(name)); - ct_test(pTest, strcmp(Device_Vendor_Name(),name) == 0); + Device_Set_Vendor_Name(name, strlen(name)); + ct_test(pTest, strcmp(Device_Vendor_Name(), name) == 0); - Device_Set_Vendor_Identifier(42); - ct_test(pTest, Device_Vendor_Identifier() == 42); + Device_Set_Vendor_Identifier(42); + ct_test(pTest, Device_Vendor_Identifier() == 42); - Device_Set_Model_Name(name,strlen(name)); - ct_test(pTest, strcmp(Device_Model_Name(),name) == 0); + Device_Set_Model_Name(name, strlen(name)); + ct_test(pTest, strcmp(Device_Model_Name(), name) == 0); - return; + return; } #ifdef TEST_DEVICE // stubs to dependencies to keep unit test simple unsigned Analog_Input_Count(void) { - return 0; + return 0; } uint32_t Analog_Input_Index_To_Instance(unsigned index) { - return index; + return index; } unsigned Analog_Output_Count(void) { - return 0; + return 0; } uint32_t Analog_Output_Index_To_Instance(unsigned index) { - return index; + return index; } uint32_t bacfile_count(void) { - return 0; + return 0; } uint32_t bacfile_index_to_instance(unsigned find_index) { - return find_index; + return find_index; } bool I_Am_Request = false; @@ -866,5 +817,3 @@ int main(void) } #endif /* TEST_DEVICE */ #endif /* TEST */ - - diff --git a/bacnet-stack/demo/object/device.h b/bacnet-stack/demo/object/device.h index 438fe4f4..563b0c92 100644 --- a/bacnet-stack/demo/object/device.h +++ b/bacnet-stack/demo/object/device.h @@ -42,78 +42,69 @@ #ifdef __cplusplus extern "C" { -#endif /* __cplusplus */ +#endif /* __cplusplus */ -uint32_t Device_Object_Instance_Number(void); -bool Device_Set_Object_Instance_Number(uint32_t object_id); -bool Device_Valid_Object_Instance_Number(uint32_t object_id); -unsigned Device_Object_List_Count(void); -bool Device_Object_List_Identifier(unsigned array_index, - int *object_type, - uint32_t *instance); + uint32_t Device_Object_Instance_Number(void); + bool Device_Set_Object_Instance_Number(uint32_t object_id); + bool Device_Valid_Object_Instance_Number(uint32_t object_id); + unsigned Device_Object_List_Count(void); + bool Device_Object_List_Identifier(unsigned array_index, + int *object_type, uint32_t * instance); -BACNET_DEVICE_STATUS Device_System_Status(void); -void Device_Set_System_Status(BACNET_DEVICE_STATUS status); + BACNET_DEVICE_STATUS Device_System_Status(void); + void Device_Set_System_Status(BACNET_DEVICE_STATUS status); -const char *Device_Vendor_Name(void); -bool Device_Set_Vendor_Name(const char *name, size_t length); + const char *Device_Vendor_Name(void); + bool Device_Set_Vendor_Name(const char *name, size_t length); -uint16_t Device_Vendor_Identifier(void); -void Device_Set_Vendor_Identifier(uint16_t vendor_id); + uint16_t Device_Vendor_Identifier(void); + void Device_Set_Vendor_Identifier(uint16_t vendor_id); -const char *Device_Model_Name(void); -bool Device_Set_Model_Name(const char *name, size_t length); + const char *Device_Model_Name(void); + bool Device_Set_Model_Name(const char *name, size_t length); -const char *Device_Firmware_Revision(void); -bool Device_Set_Firmware_Revision(const char *name, size_t length); + const char *Device_Firmware_Revision(void); + bool Device_Set_Firmware_Revision(const char *name, size_t length); -const char *Device_Application_Software_Version(void); -bool Device_Set_Application_Software_Version(const char *name, size_t length); + const char *Device_Application_Software_Version(void); + bool Device_Set_Application_Software_Version(const char *name, + size_t length); -const char *Device_Description(void); -bool Device_Set_Description(const char *name, size_t length); + const char *Device_Description(void); + bool Device_Set_Description(const char *name, size_t length); -const char *Device_Location(void); -bool Device_Set_Location(const char *name, size_t length); + const char *Device_Location(void); + bool Device_Set_Location(const char *name, size_t length); // some stack-centric constant values - no set methods -uint8_t Device_Protocol_Version(void); -uint8_t Device_Protocol_Revision(void); -uint16_t Device_Max_APDU_Length_Accepted(void); -BACNET_SEGMENTATION Device_Segmentation_Supported(void); + uint8_t Device_Protocol_Version(void); + uint8_t Device_Protocol_Revision(void); + uint16_t Device_Max_APDU_Length_Accepted(void); + BACNET_SEGMENTATION Device_Segmentation_Supported(void); -uint16_t Device_APDU_Timeout(void); -void Device_Set_APDU_Timeout(uint16_t timeout); + uint16_t Device_APDU_Timeout(void); + void Device_Set_APDU_Timeout(uint16_t timeout); -uint8_t Device_Number_Of_APDU_Retries(void); -void Device_Set_Number_Of_APDU_Retries(uint8_t retries); + uint8_t Device_Number_Of_APDU_Retries(void); + void Device_Set_Number_Of_APDU_Retries(uint8_t retries); -uint8_t Device_Database_Revision(void); -void Device_Set_Database_Revision(uint8_t revision); + uint8_t Device_Database_Revision(void); + void Device_Set_Database_Revision(uint8_t revision); -bool Device_Valid_Object_Name( - const char *object_name, - int *object_type, - uint32_t *object_instance); -char *Device_Valid_Object_Id( - int object_type, - uint32_t object_instance); + bool Device_Valid_Object_Name(const char *object_name, + int *object_type, uint32_t * object_instance); + char *Device_Valid_Object_Id(int object_type, + uint32_t object_instance); -int Device_Encode_Property_APDU( - uint8_t *apdu, - BACNET_PROPERTY_ID property, - int32_t array_index, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code); + int Device_Encode_Property_APDU(uint8_t * apdu, + BACNET_PROPERTY_ID property, + int32_t array_index, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code); -bool Device_Write_Property( - BACNET_WRITE_PROPERTY_DATA *wp_data, - BACNET_ERROR_CLASS *error_class, - BACNET_ERROR_CODE *error_code); + bool Device_Write_Property(BACNET_WRITE_PROPERTY_DATA * wp_data, + BACNET_ERROR_CLASS * error_class, BACNET_ERROR_CODE * error_code); #ifdef __cplusplus } -#endif /* __cplusplus */ - +#endif /* __cplusplus */ #endif - diff --git a/bacnet-stack/demo/readfile/readfile.c b/bacnet-stack/demo/readfile/readfile.c index bf07310b..29998625 100644 --- a/bacnet-stack/demo/readfile/readfile.c +++ b/bacnet-stack/demo/readfile/readfile.c @@ -28,7 +28,7 @@ #include #include #include -#include /* for time */ +#include /* for time */ #include #include "bactext.h" #include "iam.h" @@ -49,7 +49,7 @@ #include "txbuf.h" // buffer used for receive -static uint8_t Rx_Buf[MAX_MPDU] = {0}; +static uint8_t Rx_Buf[MAX_MPDU] = { 0 }; /* global variables used in this file */ static uint32_t Target_File_Object_Instance = BACNET_MAX_INSTANCE; @@ -60,397 +60,322 @@ static bool End_Of_File_Detected = false; static bool Error_Detected = false; static uint8_t Current_Invoke_ID = 0; -static void Atomic_Read_File_Error_Handler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - BACNET_ERROR_CLASS error_class, - BACNET_ERROR_CODE error_code) +static void Atomic_Read_File_Error_Handler(BACNET_ADDRESS * src, + uint8_t invoke_id, + BACNET_ERROR_CLASS error_class, BACNET_ERROR_CODE error_code) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("\r\nBACnet Error!\r\n"); - printf("Error Class: %s\r\n", - bactext_error_class_name(error_class)); - printf("Error Code: %s\r\n", - bactext_error_code_name(error_code)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("\r\nBACnet Error!\r\n"); + printf("Error Class: %s\r\n", bactext_error_class_name(error_class)); + printf("Error Code: %s\r\n", bactext_error_code_name(error_code)); + Error_Detected = true; } -void MyAbortHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t abort_reason) +void MyAbortHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t abort_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("\r\nBACnet Abort!\r\n"); - printf("Abort Reason: %s\r\n", - bactext_abort_reason_name(abort_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("\r\nBACnet Abort!\r\n"); + printf("Abort Reason: %s\r\n", + bactext_abort_reason_name(abort_reason)); + Error_Detected = true; } -void MyRejectHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t reject_reason) +void MyRejectHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t reject_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("\r\nBACnet Reject!\r\n"); - printf("Reject Reason: %s\r\n", - bactext_reject_reason_name(reject_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("\r\nBACnet Reject!\r\n"); + printf("Reject Reason: %s\r\n", + bactext_reject_reason_name(reject_reason)); + Error_Detected = true; } -static uint8_t Send_Atomic_Read_File_Stream( - uint32_t device_id, - uint32_t file_instance, - int fileStartPosition, - unsigned requestedOctetCount) +static uint8_t Send_Atomic_Read_File_Stream(uint32_t device_id, + uint32_t file_instance, + int fileStartPosition, unsigned requestedOctetCount) { - BACNET_ADDRESS dest; - BACNET_ADDRESS my_address; - unsigned max_apdu = 0; - uint8_t invoke_id = 0; - bool status = false; - int pdu_len = 0; - int bytes_sent = 0; - BACNET_ATOMIC_READ_FILE_DATA data; + BACNET_ADDRESS dest; + BACNET_ADDRESS my_address; + unsigned max_apdu = 0; + uint8_t invoke_id = 0; + bool status = false; + int pdu_len = 0; + int bytes_sent = 0; + BACNET_ATOMIC_READ_FILE_DATA data; - /* is the device bound? */ - status = address_get_by_device(device_id, &max_apdu, &dest); - /* is there a tsm available? */ - if (status) - status = tsm_transaction_available(); - if (status) - { - datalink_get_my_address(&my_address); - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - &my_address, - true, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); + /* is the device bound? */ + status = address_get_by_device(device_id, &max_apdu, &dest); + /* is there a tsm available? */ + if (status) + status = tsm_transaction_available(); + if (status) { + datalink_get_my_address(&my_address); + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, &my_address, true, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); - invoke_id = tsm_next_free_invokeID(); - // load the data for the encoding - data.object_type = OBJECT_FILE; - data.object_instance = file_instance; - data.access = FILE_STREAM_ACCESS; - data.type.stream.fileStartPosition = fileStartPosition; - data.type.stream.requestedOctetCount = requestedOctetCount; - pdu_len += arf_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - invoke_id, - &data); - /* will the APDU fit the target device? - note: if there is a bottleneck router in between - us and the destination, we won't know unless - we have a way to check for that and update the - max_apdu in the address binding table. */ - if ((unsigned)pdu_len < max_apdu) - { - tsm_set_confirmed_unsegmented_transaction( - invoke_id, - &dest, - &Handler_Transmit_Buffer[0], - pdu_len); - bytes_sent = datalink_send_pdu( - &dest, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send AtomicReadFile Request (%s)!\n", - strerror(errno)); + invoke_id = tsm_next_free_invokeID(); + // load the data for the encoding + data.object_type = OBJECT_FILE; + data.object_instance = file_instance; + data.access = FILE_STREAM_ACCESS; + data.type.stream.fileStartPosition = fileStartPosition; + data.type.stream.requestedOctetCount = requestedOctetCount; + pdu_len += arf_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + invoke_id, &data); + /* will the APDU fit the target device? + note: if there is a bottleneck router in between + us and the destination, we won't know unless + we have a way to check for that and update the + max_apdu in the address binding table. */ + if ((unsigned) pdu_len < max_apdu) { + tsm_set_confirmed_unsegmented_transaction(invoke_id, + &dest, &Handler_Transmit_Buffer[0], pdu_len); + bytes_sent = datalink_send_pdu(&dest, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, + "Failed to Send AtomicReadFile Request (%s)!\n", + strerror(errno)); + } else + fprintf(stderr, "Failed to Send AtomicReadFile Request " + "(payload exceeds destination maximum APDU)!\n"); } - else - fprintf(stderr,"Failed to Send AtomicReadFile Request " - "(payload exceeds destination maximum APDU)!\n"); - } - return invoke_id; + return invoke_id; } static void Send_WhoIs(uint32_t device_id) { - int pdu_len = 0; - BACNET_ADDRESS dest; - int bytes_sent = 0; + int pdu_len = 0; + BACNET_ADDRESS dest; + int bytes_sent = 0; - /* Who-Is is a global broadcast */ - datalink_get_broadcast_address(&dest); + /* Who-Is is a global broadcast */ + datalink_get_broadcast_address(&dest); - /* encode the NPDU portion of the packet */ - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - NULL, - false, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); + /* encode the NPDU portion of the packet */ + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, NULL, false, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); - /* encode the APDU portion of the packet */ - pdu_len += whois_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - device_id, - device_id); + /* encode the APDU portion of the packet */ + pdu_len += whois_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + device_id, device_id); - bytes_sent = datalink_send_pdu( - &dest, /* destination address */ - &Handler_Transmit_Buffer[0], - pdu_len); /* number of bytes of data */ - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send Who-Is Request (%s)!\n", strerror(errno)); + bytes_sent = datalink_send_pdu(&dest, /* destination address */ + &Handler_Transmit_Buffer[0], pdu_len); /* number of bytes of data */ + if (bytes_sent <= 0) + fprintf(stderr, "Failed to Send Who-Is Request (%s)!\n", + strerror(errno)); } -static void AtomicReadFileAckHandler( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src, - BACNET_CONFIRMED_SERVICE_ACK_DATA *service_data) +static void AtomicReadFileAckHandler(uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, BACNET_CONFIRMED_SERVICE_ACK_DATA * service_data) { - int len = 0; - BACNET_ATOMIC_READ_FILE_DATA data; - FILE *pFile = NULL; /* stream pointer */ - size_t octets_written = 0; + int len = 0; + BACNET_ATOMIC_READ_FILE_DATA data; + FILE *pFile = NULL; /* stream pointer */ + size_t octets_written = 0; - (void)src; /* FIXME: validate the source address matches */ - len = arf_ack_decode_service_request( - service_request, - service_len, - &data); - if (len > 0) - { - /* validate the parameters before storing data */ - if ((data.access == FILE_STREAM_ACCESS) && - (service_data->invoke_id == Current_Invoke_ID)) - { - if (data.type.stream.fileStartPosition == 0) - pFile = fopen(Local_File_Name, "wb"); - else - pFile = fopen(Local_File_Name, "rb+"); - if (pFile) - { - /* is there anything to do with this? data.stream.requestedOctetCount */ - (void)fseek(pFile, data.type.stream.fileStartPosition, SEEK_SET); - octets_written = fwrite( - octetstring_value(&data.fileData), - 1, /* unit to write in bytes - in our case, an octet is one byte */ - octetstring_length(&data.fileData), - pFile); - if (octets_written != octetstring_length(&data.fileData)) - fprintf(stderr,"Unable to write data to file \"%s\".\n", - Local_File_Name); - else - printf("\r%u bytes", - (data.type.stream.fileStartPosition + octets_written)); - fclose(pFile); - } - if (data.endOfFile) - { - End_Of_File_Detected = true; - printf("\r\n"); - } + (void) src; /* FIXME: validate the source address matches */ + len = arf_ack_decode_service_request(service_request, + service_len, &data); + if (len > 0) { + /* validate the parameters before storing data */ + if ((data.access == FILE_STREAM_ACCESS) && + (service_data->invoke_id == Current_Invoke_ID)) { + if (data.type.stream.fileStartPosition == 0) + pFile = fopen(Local_File_Name, "wb"); + else + pFile = fopen(Local_File_Name, "rb+"); + if (pFile) { + /* is there anything to do with this? data.stream.requestedOctetCount */ + (void) fseek(pFile, data.type.stream.fileStartPosition, + SEEK_SET); + octets_written = fwrite(octetstring_value(&data.fileData), 1, /* unit to write in bytes - in our case, an octet is one byte */ + octetstring_length(&data.fileData), pFile); + if (octets_written != octetstring_length(&data.fileData)) + fprintf(stderr, + "Unable to write data to file \"%s\".\n", + Local_File_Name); + else + printf("\r%u bytes", + (data.type.stream.fileStartPosition + + octets_written)); + fclose(pFile); + } + if (data.endOfFile) { + End_Of_File_Detected = true; + printf("\r\n"); + } + } } - } } -static void LocalIAmHandler( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src) +static void LocalIAmHandler(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src) { - int len = 0; - uint32_t device_id = 0; - unsigned max_apdu = 0; - int segmentation = 0; - uint16_t vendor_id = 0; + int len = 0; + uint32_t device_id = 0; + unsigned max_apdu = 0; + int segmentation = 0; + uint16_t vendor_id = 0; - (void)src; - (void)service_len; - len = iam_decode_service_request( - service_request, - &device_id, - &max_apdu, - &segmentation, - &vendor_id); - if (len != -1) - { - address_add(device_id, - max_apdu, - src); - } - else - fprintf(stderr,"!\n"); + (void) src; + (void) service_len; + len = iam_decode_service_request(service_request, + &device_id, &max_apdu, &segmentation, &vendor_id); + if (len != -1) { + address_add(device_id, max_apdu, src); + } else + fprintf(stderr, "!\n"); - return; + return; } static void Init_Service_Handlers(void) { - /* we need to handle who-is - to support dynamic device binding to us */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_WHO_IS, - handler_who_is); - /* handle i-am to support binding to other devices */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_I_AM, - LocalIAmHandler); - /* set the handler for all the services we don't implement - It is required to send the proper reject message... */ - apdu_set_unrecognized_service_handler_handler( - handler_unrecognized_service); - /* we must implement read property - it's required! */ - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property); - /* handle the data coming back from confirmed requests */ - apdu_set_confirmed_ack_handler( - SERVICE_CONFIRMED_ATOMIC_READ_FILE, - AtomicReadFileAckHandler); - /* handle any errors coming back */ - apdu_set_error_handler( - SERVICE_CONFIRMED_ATOMIC_READ_FILE, - Atomic_Read_File_Error_Handler); - apdu_set_abort_handler( - MyAbortHandler); - apdu_set_reject_handler( - MyRejectHandler); + /* we need to handle who-is + to support dynamic device binding to us */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_WHO_IS, + handler_who_is); + /* handle i-am to support binding to other devices */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_I_AM, + LocalIAmHandler); + /* set the handler for all the services we don't implement + It is required to send the proper reject message... */ + apdu_set_unrecognized_service_handler_handler + (handler_unrecognized_service); + /* we must implement read property - it's required! */ + apdu_set_confirmed_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property); + /* handle the data coming back from confirmed requests */ + apdu_set_confirmed_ack_handler(SERVICE_CONFIRMED_ATOMIC_READ_FILE, + AtomicReadFileAckHandler); + /* handle any errors coming back */ + apdu_set_error_handler(SERVICE_CONFIRMED_ATOMIC_READ_FILE, + Atomic_Read_File_Error_Handler); + apdu_set_abort_handler(MyAbortHandler); + apdu_set_reject_handler(MyRejectHandler); } int main(int argc, char *argv[]) { - BACNET_ADDRESS src = {0}; // address where message came from - uint16_t pdu_len = 0; - unsigned timeout = 100; // milliseconds - unsigned max_apdu = 0; - time_t elapsed_seconds = 0; - time_t last_seconds = 0; - time_t current_seconds = 0; - time_t timeout_seconds = 0; - int fileStartPosition = 0; - unsigned requestedOctetCount = 0; - uint8_t invoke_id = 0; - bool found = false; - uint16_t my_max_apdu = 0; - - if (argc < 4) - { - /* FIXME: what about access method - record or stream? */ - printf("%s device-instance file-instance local-name\r\n", - filename_remove_path(argv[0])); - return 0; - } - /* decode the command line parameters */ - Target_Device_Object_Instance = strtol(argv[1],NULL,0); - Target_File_Object_Instance = strtol(argv[2],NULL,0); - Local_File_Name = argv[3]; - if (Target_Device_Object_Instance >= BACNET_MAX_INSTANCE) - { - fprintf(stderr,"device-instance=%u - it must be less than %u\r\n", - Target_Device_Object_Instance,BACNET_MAX_INSTANCE); - return 1; - } - if (Target_File_Object_Instance >= BACNET_MAX_INSTANCE) - { - fprintf(stderr,"file-instance=%u - it must be less than %u\r\n", - Target_File_Object_Instance,BACNET_MAX_INSTANCE+1); - return 1; - } - /* setup my info */ - Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); - address_init(); - Init_Service_Handlers(); - /* configure standard BACnet/IP port */ - bip_set_interface("eth0"); /* for linux */ - bip_set_port(0xBAC0); - if (!bip_init()) - return 1; - /* configure the timeout values */ - last_seconds = time(NULL); - timeout_seconds = (Device_APDU_Timeout() / 1000) * - Device_Number_Of_APDU_Retries(); - /* try to bind with the device */ - Send_WhoIs(Target_Device_Object_Instance); - /* loop forever */ - for (;;) - { - /* increment timer - exit if timed out */ - current_seconds = time(NULL); + BACNET_ADDRESS src = { 0 }; // address where message came from + uint16_t pdu_len = 0; + unsigned timeout = 100; // milliseconds + unsigned max_apdu = 0; + time_t elapsed_seconds = 0; + time_t last_seconds = 0; + time_t current_seconds = 0; + time_t timeout_seconds = 0; + int fileStartPosition = 0; + unsigned requestedOctetCount = 0; + uint8_t invoke_id = 0; + bool found = false; + uint16_t my_max_apdu = 0; - /* returns 0 bytes on timeout */ - pdu_len = bip_receive( - &src, - &Rx_Buf[0], - MAX_MPDU, - timeout); - - /* process */ - if (pdu_len) - { - npdu_handler( - &src, - &Rx_Buf[0], - pdu_len); + if (argc < 4) { + /* FIXME: what about access method - record or stream? */ + printf("%s device-instance file-instance local-name\r\n", + filename_remove_path(argv[0])); + return 0; } - /* at least one second has passed */ - if (current_seconds != last_seconds) - tsm_timer_milliseconds(((current_seconds - last_seconds) * 1000)); - if (End_Of_File_Detected || Error_Detected) - break; - if (I_Am_Request) - { - I_Am_Request = false; - iam_send(&Handler_Transmit_Buffer[0]); + /* decode the command line parameters */ + Target_Device_Object_Instance = strtol(argv[1], NULL, 0); + Target_File_Object_Instance = strtol(argv[2], NULL, 0); + Local_File_Name = argv[3]; + if (Target_Device_Object_Instance >= BACNET_MAX_INSTANCE) { + fprintf(stderr, "device-instance=%u - it must be less than %u\r\n", + Target_Device_Object_Instance, BACNET_MAX_INSTANCE); + return 1; } - else - { - /* wait until the device is bound, or timeout and quit */ - found = address_bind_request( - Target_Device_Object_Instance, - &max_apdu, - &Target_Address); - if (found) - { - /* calculate the smaller of our APDU size or theirs - and remove the overhead of the APDU (about 16 octets max). - note: we could fail if there is a bottle neck (router) - and smaller MPDU in betweeen. */ - if (max_apdu < MAX_APDU) - my_max_apdu = max_apdu; - else - my_max_apdu = MAX_APDU; - requestedOctetCount = my_max_apdu - 16; - /* has the previous invoke id expired or returned? - note: invoke ID = 0 is invalid, so it will be idle */ - if ((invoke_id == 0) || tsm_invoke_id_free(invoke_id)) - { - if (invoke_id != 0) - fileStartPosition += requestedOctetCount; - /* we'll read the file in chunks - less than max_apdu to keep unsegmented */ - invoke_id = Send_Atomic_Read_File_Stream( - Target_Device_Object_Instance, - Target_File_Object_Instance, - fileStartPosition, - requestedOctetCount); - Current_Invoke_ID = invoke_id; - } - } - else - { + if (Target_File_Object_Instance >= BACNET_MAX_INSTANCE) { + fprintf(stderr, "file-instance=%u - it must be less than %u\r\n", + Target_File_Object_Instance, BACNET_MAX_INSTANCE + 1); + return 1; + } + /* setup my info */ + Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); + address_init(); + Init_Service_Handlers(); + /* configure standard BACnet/IP port */ + bip_set_interface("eth0"); /* for linux */ + bip_set_port(0xBAC0); + if (!bip_init()) + return 1; + /* configure the timeout values */ + last_seconds = time(NULL); + timeout_seconds = (Device_APDU_Timeout() / 1000) * + Device_Number_Of_APDU_Retries(); + /* try to bind with the device */ + Send_WhoIs(Target_Device_Object_Instance); + /* loop forever */ + for (;;) { /* increment timer - exit if timed out */ - elapsed_seconds += (current_seconds - last_seconds); - if (elapsed_seconds > timeout_seconds) - break; - } - } - /* keep track of time for next check */ - last_seconds = current_seconds; - } + current_seconds = time(NULL); - return 0; + /* returns 0 bytes on timeout */ + pdu_len = bip_receive(&src, &Rx_Buf[0], MAX_MPDU, timeout); + + /* process */ + if (pdu_len) { + npdu_handler(&src, &Rx_Buf[0], pdu_len); + } + /* at least one second has passed */ + if (current_seconds != last_seconds) + tsm_timer_milliseconds(((current_seconds - + last_seconds) * 1000)); + if (End_Of_File_Detected || Error_Detected) + break; + if (I_Am_Request) { + I_Am_Request = false; + iam_send(&Handler_Transmit_Buffer[0]); + } else { + /* wait until the device is bound, or timeout and quit */ + found = address_bind_request(Target_Device_Object_Instance, + &max_apdu, &Target_Address); + if (found) { + /* calculate the smaller of our APDU size or theirs + and remove the overhead of the APDU (about 16 octets max). + note: we could fail if there is a bottle neck (router) + and smaller MPDU in betweeen. */ + if (max_apdu < MAX_APDU) + my_max_apdu = max_apdu; + else + my_max_apdu = MAX_APDU; + requestedOctetCount = my_max_apdu - 16; + /* has the previous invoke id expired or returned? + note: invoke ID = 0 is invalid, so it will be idle */ + if ((invoke_id == 0) || tsm_invoke_id_free(invoke_id)) { + if (invoke_id != 0) + fileStartPosition += requestedOctetCount; + /* we'll read the file in chunks + less than max_apdu to keep unsegmented */ + invoke_id = + Send_Atomic_Read_File_Stream + (Target_Device_Object_Instance, + Target_File_Object_Instance, fileStartPosition, + requestedOctetCount); + Current_Invoke_ID = invoke_id; + } + } else { + /* increment timer - exit if timed out */ + elapsed_seconds += (current_seconds - last_seconds); + if (elapsed_seconds > timeout_seconds) + break; + } + } + /* keep track of time for next check */ + last_seconds = current_seconds; + } + + return 0; } diff --git a/bacnet-stack/demo/readprop/readprop.c b/bacnet-stack/demo/readprop/readprop.c index 0b5ae923..2ef8a016 100644 --- a/bacnet-stack/demo/readprop/readprop.c +++ b/bacnet-stack/demo/readprop/readprop.c @@ -28,7 +28,7 @@ #include #include #include -#include /* for time */ +#include /* for time */ #include #include "bactext.h" #include "iam.h" @@ -50,7 +50,7 @@ #include "txbuf.h" // buffer used for receive -static uint8_t Rx_Buf[MAX_MPDU] = {0}; +static uint8_t Rx_Buf[MAX_MPDU] = { 0 }; /* global variables used in this file */ static uint32_t Target_Device_Object_Instance = BACNET_MAX_INSTANCE; @@ -62,211 +62,176 @@ static int32_t Target_Object_Index = BACNET_ARRAY_ALL; static BACNET_ADDRESS Target_Address; static bool Error_Detected = false; -static void MyErrorHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - BACNET_ERROR_CLASS error_class, - BACNET_ERROR_CODE error_code) +static void MyErrorHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, + BACNET_ERROR_CLASS error_class, BACNET_ERROR_CODE error_code) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("BACnet Error: %s: %s\r\n", - bactext_error_class_name(error_class), - bactext_error_code_name(error_code)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("BACnet Error: %s: %s\r\n", + bactext_error_class_name(error_class), + bactext_error_code_name(error_code)); + Error_Detected = true; } -void MyAbortHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t abort_reason) +void MyAbortHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t abort_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("BACnet Abort: %s\r\n", - bactext_abort_reason_name(abort_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("BACnet Abort: %s\r\n", + bactext_abort_reason_name(abort_reason)); + Error_Detected = true; } -void MyRejectHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t reject_reason) +void MyRejectHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t reject_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("BACnet Reject: %s\r\n", - bactext_reject_reason_name(reject_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("BACnet Reject: %s\r\n", + bactext_reject_reason_name(reject_reason)); + Error_Detected = true; } static void Init_Service_Handlers(void) { - /* we need to handle who-is - to support dynamic device binding to us */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_WHO_IS, - handler_who_is); - /* handle i-am to support binding to other devices */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_I_AM, - handler_i_am_bind); - /* set the handler for all the services we don't implement - It is required to send the proper reject message... */ - apdu_set_unrecognized_service_handler_handler( - handler_unrecognized_service); - /* we must implement read property - it's required! */ - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property); - /* handle the data coming back from confirmed requests */ - apdu_set_confirmed_ack_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property_ack); - /* handle any errors coming back */ - apdu_set_error_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - MyErrorHandler); - apdu_set_abort_handler( - MyAbortHandler); - apdu_set_reject_handler( - MyRejectHandler); + /* we need to handle who-is + to support dynamic device binding to us */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_WHO_IS, + handler_who_is); + /* handle i-am to support binding to other devices */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_I_AM, + handler_i_am_bind); + /* set the handler for all the services we don't implement + It is required to send the proper reject message... */ + apdu_set_unrecognized_service_handler_handler + (handler_unrecognized_service); + /* we must implement read property - it's required! */ + apdu_set_confirmed_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property); + /* handle the data coming back from confirmed requests */ + apdu_set_confirmed_ack_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property_ack); + /* handle any errors coming back */ + apdu_set_error_handler(SERVICE_CONFIRMED_READ_PROPERTY, + MyErrorHandler); + apdu_set_abort_handler(MyAbortHandler); + apdu_set_reject_handler(MyRejectHandler); } int main(int argc, char *argv[]) { - BACNET_ADDRESS src = {0}; // address where message came from - uint16_t pdu_len = 0; - unsigned timeout = 100; // milliseconds - unsigned max_apdu = 0; - time_t elapsed_seconds = 0; - time_t last_seconds = 0; - time_t current_seconds = 0; - time_t timeout_seconds = 0; - uint8_t invoke_id = 0; - bool found = false; + BACNET_ADDRESS src = { 0 }; // address where message came from + uint16_t pdu_len = 0; + unsigned timeout = 100; // milliseconds + unsigned max_apdu = 0; + time_t elapsed_seconds = 0; + time_t last_seconds = 0; + time_t current_seconds = 0; + time_t timeout_seconds = 0; + uint8_t invoke_id = 0; + bool found = false; - if (argc < 5) - { - printf("%s device-instance object-type object-instance property [index]\r\n", - filename_remove_path(argv[0])); - return 0; - } - /* decode the command line parameters */ - Target_Device_Object_Instance = strtol(argv[1],NULL,0); - Target_Object_Type = strtol(argv[2],NULL,0); - Target_Object_Instance = strtol(argv[3],NULL,0); - Target_Object_Property = strtol(argv[4],NULL,0); - if (argc > 5) - Target_Object_Index = strtol(argv[5],NULL,0); - if (Target_Device_Object_Instance >= BACNET_MAX_INSTANCE) - { - fprintf(stderr,"device-instance=%u - it must be less than %u\r\n", - Target_Device_Object_Instance,BACNET_MAX_INSTANCE); - return 1; - } - if (Target_Object_Type > MAX_BACNET_OBJECT_TYPE) - { - fprintf(stderr,"object-type=%u - it must be less than %u\r\n", - Target_Object_Type,MAX_BACNET_OBJECT_TYPE+1); - return 1; - } - if (Target_Object_Instance > BACNET_MAX_INSTANCE) - { - fprintf(stderr,"object-instance=%u - it must be less than %u\r\n", - Target_Object_Instance,BACNET_MAX_INSTANCE+1); - return 1; - } - if (Target_Object_Property > MAX_BACNET_PROPERTY_ID) - { - fprintf(stderr,"object-type=%u - it must be less than %u\r\n", - Target_Object_Property,MAX_BACNET_PROPERTY_ID+1); - return 1; - } - - /* setup my info */ - Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); - address_init(); - Init_Service_Handlers(); - /* configure standard BACnet/IP port */ - bip_set_interface("eth0"); /* for linux */ - bip_set_port(0xBAC0); - if (!bip_init()) - return 1; - /* configure the timeout values */ - last_seconds = time(NULL); - timeout_seconds = (Device_APDU_Timeout() / 1000) * - Device_Number_Of_APDU_Retries(); - /* no need to spam the world */ - I_Am_Request = false; - /* try to bind with the device */ - Send_WhoIs(Target_Device_Object_Instance,Target_Device_Object_Instance); - /* loop forever */ - for (;;) - { - /* increment timer - exit if timed out */ - current_seconds = time(NULL); - - /* returns 0 bytes on timeout */ - pdu_len = bip_receive( - &src, - &Rx_Buf[0], - MAX_MPDU, - timeout); - - /* process */ - if (pdu_len) - { - npdu_handler( - &src, - &Rx_Buf[0], - pdu_len); + if (argc < 5) { + printf + ("%s device-instance object-type object-instance property [index]\r\n", + filename_remove_path(argv[0])); + return 0; } - /* at least one second has passed */ - if (current_seconds != last_seconds) - tsm_timer_milliseconds(((current_seconds - last_seconds) * 1000)); - if (Error_Detected) - break; - if (I_Am_Request) - { - I_Am_Request = false; - iam_send(&Handler_Transmit_Buffer[0]); + /* decode the command line parameters */ + Target_Device_Object_Instance = strtol(argv[1], NULL, 0); + Target_Object_Type = strtol(argv[2], NULL, 0); + Target_Object_Instance = strtol(argv[3], NULL, 0); + Target_Object_Property = strtol(argv[4], NULL, 0); + if (argc > 5) + Target_Object_Index = strtol(argv[5], NULL, 0); + if (Target_Device_Object_Instance >= BACNET_MAX_INSTANCE) { + fprintf(stderr, "device-instance=%u - it must be less than %u\r\n", + Target_Device_Object_Instance, BACNET_MAX_INSTANCE); + return 1; } - else - { - /* wait until the device is bound, or timeout and quit */ - found = address_bind_request( - Target_Device_Object_Instance, - &max_apdu, - &Target_Address); - if (found) - { - if (invoke_id == 0) - { - invoke_id = Send_Read_Property_Request( - Target_Device_Object_Instance, - Target_Object_Type, - Target_Object_Instance, - Target_Object_Property, - Target_Object_Index); - } - else if (tsm_invoke_id_free(invoke_id)) - break; - } - else - { + if (Target_Object_Type > MAX_BACNET_OBJECT_TYPE) { + fprintf(stderr, "object-type=%u - it must be less than %u\r\n", + Target_Object_Type, MAX_BACNET_OBJECT_TYPE + 1); + return 1; + } + if (Target_Object_Instance > BACNET_MAX_INSTANCE) { + fprintf(stderr, "object-instance=%u - it must be less than %u\r\n", + Target_Object_Instance, BACNET_MAX_INSTANCE + 1); + return 1; + } + if (Target_Object_Property > MAX_BACNET_PROPERTY_ID) { + fprintf(stderr, "object-type=%u - it must be less than %u\r\n", + Target_Object_Property, MAX_BACNET_PROPERTY_ID + 1); + return 1; + } + + /* setup my info */ + Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); + address_init(); + Init_Service_Handlers(); + /* configure standard BACnet/IP port */ + bip_set_interface("eth0"); /* for linux */ + bip_set_port(0xBAC0); + if (!bip_init()) + return 1; + /* configure the timeout values */ + last_seconds = time(NULL); + timeout_seconds = (Device_APDU_Timeout() / 1000) * + Device_Number_Of_APDU_Retries(); + /* no need to spam the world */ + I_Am_Request = false; + /* try to bind with the device */ + Send_WhoIs(Target_Device_Object_Instance, + Target_Device_Object_Instance); + /* loop forever */ + for (;;) { /* increment timer - exit if timed out */ - elapsed_seconds += (current_seconds - last_seconds); - if (elapsed_seconds > timeout_seconds) - break; - } - } - /* keep track of time for next check */ - last_seconds = current_seconds; - } + current_seconds = time(NULL); - return 0; + /* returns 0 bytes on timeout */ + pdu_len = bip_receive(&src, &Rx_Buf[0], MAX_MPDU, timeout); + + /* process */ + if (pdu_len) { + npdu_handler(&src, &Rx_Buf[0], pdu_len); + } + /* at least one second has passed */ + if (current_seconds != last_seconds) + tsm_timer_milliseconds(((current_seconds - + last_seconds) * 1000)); + if (Error_Detected) + break; + if (I_Am_Request) { + I_Am_Request = false; + iam_send(&Handler_Transmit_Buffer[0]); + } else { + /* wait until the device is bound, or timeout and quit */ + found = address_bind_request(Target_Device_Object_Instance, + &max_apdu, &Target_Address); + if (found) { + if (invoke_id == 0) { + invoke_id = + Send_Read_Property_Request + (Target_Device_Object_Instance, Target_Object_Type, + Target_Object_Instance, Target_Object_Property, + Target_Object_Index); + } else if (tsm_invoke_id_free(invoke_id)) + break; + } else { + /* increment timer - exit if timed out */ + elapsed_seconds += (current_seconds - last_seconds); + if (elapsed_seconds > timeout_seconds) + break; + } + } + /* keep track of time for next check */ + last_seconds = current_seconds; + } + + return 0; } diff --git a/bacnet-stack/demo/reinit/main.c b/bacnet-stack/demo/reinit/main.c index 0bcca5da..8c5231c5 100644 --- a/bacnet-stack/demo/reinit/main.c +++ b/bacnet-stack/demo/reinit/main.c @@ -28,7 +28,7 @@ #include #include #include -#include /* for time */ +#include /* for time */ #include #include "bactext.h" #include "iam.h" @@ -51,253 +51,216 @@ #include "txbuf.h" // buffer used for receive -static uint8_t Rx_Buf[MAX_MPDU] = {0}; +static uint8_t Rx_Buf[MAX_MPDU] = { 0 }; /* global variables used in this file */ static uint32_t Target_Device_Object_Instance = BACNET_MAX_INSTANCE; static BACNET_ADDRESS Target_Address; -static BACNET_REINITIALIZED_STATE Reinitialize_State = BACNET_REINIT_COLDSTART; +static BACNET_REINITIALIZED_STATE Reinitialize_State = + BACNET_REINIT_COLDSTART; static char *Reinitialize_Password = NULL; static bool Error_Detected = false; -static void MyErrorHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - BACNET_ERROR_CLASS error_class, - BACNET_ERROR_CODE error_code) +static void MyErrorHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, + BACNET_ERROR_CLASS error_class, BACNET_ERROR_CODE error_code) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("BACnet Error: %s: %s\r\n", - bactext_error_class_name(error_class), - bactext_error_code_name(error_code)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("BACnet Error: %s: %s\r\n", + bactext_error_class_name(error_class), + bactext_error_code_name(error_code)); + Error_Detected = true; } -void MyAbortHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t abort_reason) +void MyAbortHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t abort_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("BACnet Abort: %s\r\n", - bactext_abort_reason_name(abort_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("BACnet Abort: %s\r\n", + bactext_abort_reason_name(abort_reason)); + Error_Detected = true; } -void MyRejectHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t reject_reason) +void MyRejectHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t reject_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("BACnet Reject: %s\r\n", - bactext_reject_reason_name(reject_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("BACnet Reject: %s\r\n", + bactext_reject_reason_name(reject_reason)); + Error_Detected = true; } -void MyReinitializeDeviceSimpleAckHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id) +void MyReinitializeDeviceSimpleAckHandler(BACNET_ADDRESS * src, + uint8_t invoke_id) { - (void)src; - (void)invoke_id; - printf("ReinitializeDevice Acknowledged!\r\n"); + (void) src; + (void) invoke_id; + printf("ReinitializeDevice Acknowledged!\r\n"); } static void Init_Service_Handlers(void) { - /* we need to handle who-is - to support dynamic device binding to us */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_WHO_IS, - handler_who_is); - /* handle i-am to support binding to other devices */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_I_AM, - handler_i_am_bind); - /* set the handler for all the services we don't implement - It is required to send the proper reject message... */ - apdu_set_unrecognized_service_handler_handler( - handler_unrecognized_service); - /* we must implement read property - it's required! */ - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property); - /* handle the ack coming back */ - apdu_set_confirmed_simple_ack_handler( - SERVICE_CONFIRMED_REINITIALIZE_DEVICE, - MyReinitializeDeviceSimpleAckHandler); - /* handle any errors coming back */ - apdu_set_error_handler( - SERVICE_CONFIRMED_REINITIALIZE_DEVICE, - MyErrorHandler); - apdu_set_abort_handler( - MyAbortHandler); - apdu_set_reject_handler( - MyRejectHandler); + /* we need to handle who-is + to support dynamic device binding to us */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_WHO_IS, + handler_who_is); + /* handle i-am to support binding to other devices */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_I_AM, + handler_i_am_bind); + /* set the handler for all the services we don't implement + It is required to send the proper reject message... */ + apdu_set_unrecognized_service_handler_handler + (handler_unrecognized_service); + /* we must implement read property - it's required! */ + apdu_set_confirmed_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property); + /* handle the ack coming back */ + apdu_set_confirmed_simple_ack_handler + (SERVICE_CONFIRMED_REINITIALIZE_DEVICE, + MyReinitializeDeviceSimpleAckHandler); + /* handle any errors coming back */ + apdu_set_error_handler(SERVICE_CONFIRMED_REINITIALIZE_DEVICE, + MyErrorHandler); + apdu_set_abort_handler(MyAbortHandler); + apdu_set_reject_handler(MyRejectHandler); } #ifdef BIP_DEBUG -static void print_address( - char *name, - BACNET_ADDRESS *dest) // destination address +static void print_address(char *name, BACNET_ADDRESS * dest) // destination address { - int i = 0; // counter + int i = 0; // counter - if (dest) - { - printf("%s: ",name); - for (i = 0; i < dest->mac_len; i++) - { - printf("%02X",dest->mac[i]); + if (dest) { + printf("%s: ", name); + for (i = 0; i < dest->mac_len; i++) { + printf("%02X", dest->mac[i]); + } + printf("\n"); } - printf("\n"); - } } #endif int main(int argc, char *argv[]) { - BACNET_ADDRESS src = {0}; // address where message came from - uint16_t pdu_len = 0; - unsigned timeout = 100; // milliseconds - unsigned max_apdu = 0; - time_t elapsed_seconds = 0; - time_t last_seconds = 0; - time_t current_seconds = 0; - time_t timeout_seconds = 0; - uint8_t invoke_id = 0; - bool found = false; - #ifdef BIP_DEBUG - BACNET_ADDRESS my_address, broadcast_address; - #endif - - if (argc < 3) - { - /* note: priority 16 and 0 should produce the same end results... */ - printf( - "Usage: %s device-instance state [password]\r\n" - "Send BACnet ReinitializeDevice service to device.\r\n" - "\r\n" - "The device-instance can be 0 to %d.\r\n" - "Possible state values:\r\n" - " 0=coldstart\r\n" - " 1=warmstart\r\n" - " 2=startbackup\r\n" - " 3=endbackup\r\n" - " 4=startrestore\r\n" - " 5=endrestore\r\n" - " 6=abortrestore\r\n" - "The optional password is a character string of 1 to 20 characters.\r\n", - filename_remove_path(argv[0]), - BACNET_MAX_INSTANCE-1); - return 0; - } - /* decode the command line parameters */ - Target_Device_Object_Instance = strtol(argv[1],NULL,0); - Reinitialize_State = strtol(argv[2],NULL,0); - /* optional password */ - if (argc > 3) - Reinitialize_Password = argv[3]; - - if (Target_Device_Object_Instance >= BACNET_MAX_INSTANCE) - { - fprintf(stderr,"device-instance=%u - it must be less than %u\r\n", - Target_Device_Object_Instance,BACNET_MAX_INSTANCE); - return 1; - } - - /* setup my info */ - Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); - address_init(); - Init_Service_Handlers(); - /* configure standard BACnet/IP port */ - bip_set_interface("eth0"); /* for linux */ - bip_set_port(0xBAC0); - if (!bip_init()) - return 1; - #ifdef BIP_DEBUG - datalink_get_broadcast_address(&broadcast_address); - print_address("Broadcast",&broadcast_address); - datalink_get_my_address(&my_address); - print_address("Address",&my_address); - #endif - /* configure the timeout values */ - last_seconds = time(NULL); - timeout_seconds = (Device_APDU_Timeout() / 1000) * - Device_Number_Of_APDU_Retries(); - /* don't send an I-Am unless asked */ - I_Am_Request = false; - /* try to bind with the device */ - Send_WhoIs(Target_Device_Object_Instance,Target_Device_Object_Instance); - /* loop forever */ - for (;;) - { - /* increment timer - exit if timed out */ - current_seconds = time(NULL); + BACNET_ADDRESS src = { 0 }; // address where message came from + uint16_t pdu_len = 0; + unsigned timeout = 100; // milliseconds + unsigned max_apdu = 0; + time_t elapsed_seconds = 0; + time_t last_seconds = 0; + time_t current_seconds = 0; + time_t timeout_seconds = 0; + uint8_t invoke_id = 0; + bool found = false; +#ifdef BIP_DEBUG + BACNET_ADDRESS my_address, broadcast_address; +#endif - /* returns 0 bytes on timeout */ - pdu_len = bip_receive( - &src, - &Rx_Buf[0], - MAX_MPDU, - timeout); + if (argc < 3) { + /* note: priority 16 and 0 should produce the same end results... */ + printf("Usage: %s device-instance state [password]\r\n" + "Send BACnet ReinitializeDevice service to device.\r\n" + "\r\n" + "The device-instance can be 0 to %d.\r\n" + "Possible state values:\r\n" + " 0=coldstart\r\n" + " 1=warmstart\r\n" + " 2=startbackup\r\n" + " 3=endbackup\r\n" + " 4=startrestore\r\n" + " 5=endrestore\r\n" + " 6=abortrestore\r\n" + "The optional password is a character string of 1 to 20 characters.\r\n", + filename_remove_path(argv[0]), BACNET_MAX_INSTANCE - 1); + return 0; + } + /* decode the command line parameters */ + Target_Device_Object_Instance = strtol(argv[1], NULL, 0); + Reinitialize_State = strtol(argv[2], NULL, 0); + /* optional password */ + if (argc > 3) + Reinitialize_Password = argv[3]; - /* process */ - if (pdu_len) - { - npdu_handler( - &src, - &Rx_Buf[0], - pdu_len); + if (Target_Device_Object_Instance >= BACNET_MAX_INSTANCE) { + fprintf(stderr, "device-instance=%u - it must be less than %u\r\n", + Target_Device_Object_Instance, BACNET_MAX_INSTANCE); + return 1; } - /* at least one second has passed */ - if (current_seconds != last_seconds) - tsm_timer_milliseconds(((current_seconds - last_seconds) * 1000)); - if (Error_Detected) - break; - if (I_Am_Request) - { - I_Am_Request = false; - iam_send(&Handler_Transmit_Buffer[0]); - } - else - { - /* wait until the device is bound, or timeout and quit */ - found = address_bind_request( - Target_Device_Object_Instance, - &max_apdu, - &Target_Address); - if (found) - { - if (invoke_id == 0) - { - invoke_id = Send_Reinitialize_Device_Request( - Target_Device_Object_Instance, - Reinitialize_State, - Reinitialize_Password); - } - else if (tsm_invoke_id_free(invoke_id)) - break; - } - else - { + + /* setup my info */ + Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); + address_init(); + Init_Service_Handlers(); + /* configure standard BACnet/IP port */ + bip_set_interface("eth0"); /* for linux */ + bip_set_port(0xBAC0); + if (!bip_init()) + return 1; +#ifdef BIP_DEBUG + datalink_get_broadcast_address(&broadcast_address); + print_address("Broadcast", &broadcast_address); + datalink_get_my_address(&my_address); + print_address("Address", &my_address); +#endif + /* configure the timeout values */ + last_seconds = time(NULL); + timeout_seconds = (Device_APDU_Timeout() / 1000) * + Device_Number_Of_APDU_Retries(); + /* don't send an I-Am unless asked */ + I_Am_Request = false; + /* try to bind with the device */ + Send_WhoIs(Target_Device_Object_Instance, + Target_Device_Object_Instance); + /* loop forever */ + for (;;) { /* increment timer - exit if timed out */ - elapsed_seconds += (current_seconds - last_seconds); - if (elapsed_seconds > timeout_seconds) - break; - } - } - /* keep track of time for next check */ - last_seconds = current_seconds; - } + current_seconds = time(NULL); - return 0; + /* returns 0 bytes on timeout */ + pdu_len = bip_receive(&src, &Rx_Buf[0], MAX_MPDU, timeout); + + /* process */ + if (pdu_len) { + npdu_handler(&src, &Rx_Buf[0], pdu_len); + } + /* at least one second has passed */ + if (current_seconds != last_seconds) + tsm_timer_milliseconds(((current_seconds - + last_seconds) * 1000)); + if (Error_Detected) + break; + if (I_Am_Request) { + I_Am_Request = false; + iam_send(&Handler_Transmit_Buffer[0]); + } else { + /* wait until the device is bound, or timeout and quit */ + found = address_bind_request(Target_Device_Object_Instance, + &max_apdu, &Target_Address); + if (found) { + if (invoke_id == 0) { + invoke_id = + Send_Reinitialize_Device_Request + (Target_Device_Object_Instance, Reinitialize_State, + Reinitialize_Password); + } else if (tsm_invoke_id_free(invoke_id)) + break; + } else { + /* increment timer - exit if timed out */ + elapsed_seconds += (current_seconds - last_seconds); + if (elapsed_seconds > timeout_seconds) + break; + } + } + /* keep track of time for next check */ + last_seconds = current_seconds; + } + + return 0; } diff --git a/bacnet-stack/demo/server/server.c b/bacnet-stack/demo/server/server.c index 68030a22..ce345d53 100644 --- a/bacnet-stack/demo/server/server.c +++ b/bacnet-stack/demo/server/server.c @@ -48,136 +48,116 @@ /* This is an example application using the BACnet Stack */ /* buffers used for receiving */ -static uint8_t Rx_Buf[MAX_MPDU] = {0}; - +static uint8_t Rx_Buf[MAX_MPDU] = { 0 }; + static void Init_Service_Handlers(void) { - /* we need to handle who-is to support dynamic device binding */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_WHO_IS, - handler_who_is); - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_WHO_HAS, - handler_who_has); - /* set the handler for all the services we don't implement */ - /* It is required to send the proper reject message... */ - apdu_set_unrecognized_service_handler_handler( - handler_unrecognized_service); - /* Set the handlers for any confirmed services that we support. */ - /* We must implement read property - it's required! */ - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property); - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_WRITE_PROPERTY, - handler_write_property); - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_ATOMIC_READ_FILE, - handler_atomic_read_file); - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_REINITIALIZE_DEVICE, - handler_reinitialize_device); - /* handle communication so we can shutup when asked */ - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_DEVICE_COMMUNICATION_CONTROL, - handler_device_communication_control); + /* we need to handle who-is to support dynamic device binding */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_WHO_IS, + handler_who_is); + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_WHO_HAS, + handler_who_has); + /* set the handler for all the services we don't implement */ + /* It is required to send the proper reject message... */ + apdu_set_unrecognized_service_handler_handler + (handler_unrecognized_service); + /* Set the handlers for any confirmed services that we support. */ + /* We must implement read property - it's required! */ + apdu_set_confirmed_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property); + apdu_set_confirmed_handler(SERVICE_CONFIRMED_WRITE_PROPERTY, + handler_write_property); + apdu_set_confirmed_handler(SERVICE_CONFIRMED_ATOMIC_READ_FILE, + handler_atomic_read_file); + apdu_set_confirmed_handler(SERVICE_CONFIRMED_REINITIALIZE_DEVICE, + handler_reinitialize_device); + /* handle communication so we can shutup when asked */ + apdu_set_confirmed_handler + (SERVICE_CONFIRMED_DEVICE_COMMUNICATION_CONTROL, + handler_device_communication_control); } static void cleanup(void) { - datalink_cleanup(); + datalink_cleanup(); } -static void print_address( - char *name, - BACNET_ADDRESS *dest) // destination address +static void print_address(char *name, BACNET_ADDRESS * dest) // destination address { - int i = 0; // counter + int i = 0; // counter - if (dest) - { - printf("%s: ",name); - for (i = 0; i < dest->mac_len; i++) - { - printf("%02X",dest->mac[i]); + if (dest) { + printf("%s: ", name); + for (i = 0; i < dest->mac_len; i++) { + printf("%02X", dest->mac[i]); + } + printf("\n"); } - printf("\n"); - } } int main(int argc, char *argv[]) { - BACNET_ADDRESS src = {0}; // address where message came from - uint16_t pdu_len = 0; - unsigned timeout = 100; // milliseconds - BACNET_ADDRESS my_address, broadcast_address; - time_t last_seconds = 0; - time_t current_seconds = 0; + BACNET_ADDRESS src = { 0 }; // address where message came from + uint16_t pdu_len = 0; + unsigned timeout = 100; // milliseconds + BACNET_ADDRESS my_address, broadcast_address; + time_t last_seconds = 0; + time_t current_seconds = 0; - /* allow the device ID to be set */ - if (argc > 1) - Device_Set_Object_Instance_Number(strtol(argv[1],NULL,0)); - if (argc > 2) - bip_set_port(strtol(argv[2],NULL,0)); - printf("BACnet Server Demo - Device #%u\r\n", - Device_Object_Instance_Number()); - Init_Service_Handlers(); - #ifdef BACDL_ETHERNET - // init the physical layer - if (!ethernet_init("eth0")) - return 1; - #endif - #ifdef BACDL_BIP - bip_set_interface("eth0"); - if (!bip_init()) - return 1; - printf("bip: using port %hu\r\n",bip_get_port()); - #endif - #ifdef BACDL_ARCNET - if (!arcnet_init("arc0")) - return 1; - #endif - datalink_get_broadcast_address(&broadcast_address); - print_address("Broadcast",&broadcast_address); - datalink_get_my_address(&my_address); - print_address("Address",&my_address); - atexit(cleanup); - /* configure the timeout values */ - last_seconds = time(NULL); - /* broadcast an I-Am on startup */ - I_Am_Request = true; - // loop forever - for (;;) - { - // input - current_seconds = time(NULL); + /* allow the device ID to be set */ + if (argc > 1) + Device_Set_Object_Instance_Number(strtol(argv[1], NULL, 0)); + if (argc > 2) + bip_set_port(strtol(argv[2], NULL, 0)); + printf("BACnet Server Demo - Device #%u\r\n", + Device_Object_Instance_Number()); + Init_Service_Handlers(); +#ifdef BACDL_ETHERNET + // init the physical layer + if (!ethernet_init("eth0")) + return 1; +#endif +#ifdef BACDL_BIP + bip_set_interface("eth0"); + if (!bip_init()) + return 1; + printf("bip: using port %hu\r\n", bip_get_port()); +#endif +#ifdef BACDL_ARCNET + if (!arcnet_init("arc0")) + return 1; +#endif + datalink_get_broadcast_address(&broadcast_address); + print_address("Broadcast", &broadcast_address); + datalink_get_my_address(&my_address); + print_address("Address", &my_address); + atexit(cleanup); + /* configure the timeout values */ + last_seconds = time(NULL); + /* broadcast an I-Am on startup */ + I_Am_Request = true; + // loop forever + for (;;) { + // input + current_seconds = time(NULL); - // returns 0 bytes on timeout - pdu_len = datalink_receive( - &src, - &Rx_Buf[0], - MAX_MPDU, - timeout); + // returns 0 bytes on timeout + pdu_len = datalink_receive(&src, &Rx_Buf[0], MAX_MPDU, timeout); - // process - if (pdu_len) - { - npdu_handler( - &src, - &Rx_Buf[0], - pdu_len); + // process + if (pdu_len) { + npdu_handler(&src, &Rx_Buf[0], pdu_len); + } + /* at least one second has passed */ + if (current_seconds != last_seconds) + dcc_timer_seconds(current_seconds - last_seconds); + /* send out the I-Am if requested */ + if (I_Am_Request) { + I_Am_Request = false; + iam_send(&Handler_Transmit_Buffer[0]); + } + // output + + // blink LEDs, Turn on or off outputs, etc } - /* at least one second has passed */ - if (current_seconds != last_seconds) - dcc_timer_seconds(current_seconds - last_seconds); - /* send out the I-Am if requested */ - if (I_Am_Request) - { - I_Am_Request = false; - iam_send(&Handler_Transmit_Buffer[0]); - } - // output - - // blink LEDs, Turn on or off outputs, etc - } } diff --git a/bacnet-stack/demo/whohas/main.c b/bacnet-stack/demo/whohas/main.c index 5c329477..c27927fe 100644 --- a/bacnet-stack/demo/whohas/main.c +++ b/bacnet-stack/demo/whohas/main.c @@ -28,7 +28,7 @@ #include #include #include -#include /* for time */ +#include /* for time */ #include #include "bactext.h" #include "iam.h" @@ -50,7 +50,7 @@ #include "txbuf.h" // buffer used for receive -static uint8_t Rx_Buf[MAX_MPDU] = {0}; +static uint8_t Rx_Buf[MAX_MPDU] = { 0 }; /* global variables used in this file */ static BACNET_OBJECT_TYPE Target_Object_Type = MAX_BACNET_OBJECT_TYPE; @@ -59,191 +59,158 @@ static char *Target_Object_Name = NULL; static bool Error_Detected = false; -void MyAbortHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t abort_reason) +void MyAbortHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t abort_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("BACnet Abort: %s\r\n", - bactext_abort_reason_name(abort_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("BACnet Abort: %s\r\n", + bactext_abort_reason_name(abort_reason)); + Error_Detected = true; } -void MyRejectHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t reject_reason) +void MyRejectHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t reject_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("BACnet Reject: %s\r\n", - bactext_reject_reason_name(reject_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("BACnet Reject: %s\r\n", + bactext_reject_reason_name(reject_reason)); + Error_Detected = true; } static void Init_Service_Handlers(void) { - /* we need to handle who-is - to support dynamic device binding to us */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_WHO_IS, - handler_who_is); - /* set the handler for all the services we don't implement - It is required to send the proper reject message... */ - apdu_set_unrecognized_service_handler_handler( - handler_unrecognized_service); - /* we must implement read property - it's required! */ - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property); - /* handle the reply (request) coming back */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_I_HAVE, - handler_i_have); - /* handle any errors coming back */ - apdu_set_abort_handler( - MyAbortHandler); - apdu_set_reject_handler( - MyRejectHandler); + /* we need to handle who-is + to support dynamic device binding to us */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_WHO_IS, + handler_who_is); + /* set the handler for all the services we don't implement + It is required to send the proper reject message... */ + apdu_set_unrecognized_service_handler_handler + (handler_unrecognized_service); + /* we must implement read property - it's required! */ + apdu_set_confirmed_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property); + /* handle the reply (request) coming back */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_I_HAVE, + handler_i_have); + /* handle any errors coming back */ + apdu_set_abort_handler(MyAbortHandler); + apdu_set_reject_handler(MyRejectHandler); } #ifdef BIP_DEBUG -static void print_address( - char *name, - BACNET_ADDRESS *dest) // destination address +static void print_address(char *name, BACNET_ADDRESS * dest) // destination address { - int i = 0; // counter + int i = 0; // counter - if (dest) - { - printf("%s: ",name); - for (i = 0; i < dest->mac_len; i++) - { - printf("%02X",dest->mac[i]); + if (dest) { + printf("%s: ", name); + for (i = 0; i < dest->mac_len; i++) { + printf("%02X", dest->mac[i]); + } + printf("\n"); } - printf("\n"); - } } #endif int main(int argc, char *argv[]) { - BACNET_ADDRESS src = {0}; // address where message came from - uint16_t pdu_len = 0; - unsigned timeout = 100; // milliseconds - time_t elapsed_seconds = 0; - time_t last_seconds = 0; - time_t current_seconds = 0; - time_t timeout_seconds = 0; - #ifdef BIP_DEBUG - BACNET_ADDRESS my_address, broadcast_address; - #endif - - if (argc < 2) - { - /* note: priority 16 and 0 should produce the same end results... */ - printf( - "Usage: %s \r\n" - "Send BACnet WhoHas request to devices, and wait for responses.\r\n" - "\r\n" - "Use either:\r\n" - "The object-type can be 0 to %d.\r\n" - "The object-instance can be 0 to %d.\r\n" - "or:\r\n" - "The object-name can be any string of characters.\r\n", - filename_remove_path(argv[0]), - MAX_BACNET_OBJECT_TYPE-1, - BACNET_MAX_INSTANCE); - return 0; - } - /* decode the command line parameters */ - if (argc < 3) - { - Target_Object_Name = argv[1]; - } - else - { - Target_Object_Type = strtol(argv[1],NULL,0); - Target_Object_Instance = strtol(argv[2],NULL,0); - if (Target_Object_Instance > BACNET_MAX_INSTANCE) - { - fprintf(stderr,"object-instance=%u - it must be less than %u\r\n", - Target_Object_Instance,BACNET_MAX_INSTANCE+1); - return 1; - } - if (Target_Object_Type > MAX_BACNET_OBJECT_TYPE) - { - fprintf(stderr,"object-type=%u - it must be less than %u\r\n", - Target_Object_Type,MAX_BACNET_OBJECT_TYPE+1); - return 1; - } - } - /* setup my info */ - Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); - Init_Service_Handlers(); - /* configure standard BACnet/IP port */ - bip_set_interface("eth0"); /* for linux */ - bip_set_port(0xBAC0); - if (!bip_init()) - return 1; - #ifdef BIP_DEBUG - datalink_get_broadcast_address(&broadcast_address); - print_address("Broadcast",&broadcast_address); - datalink_get_my_address(&my_address); - print_address("Address",&my_address); - #endif - /* configure the timeout values */ - last_seconds = time(NULL); - timeout_seconds = Device_APDU_Timeout() / 1000; - /* don't send an I-Am unless asked */ - I_Am_Request = false; - /* send the request */ - if (argc < 3) - Send_WhoHas_Name(-1, -1, Target_Object_Name); - else - Send_WhoHas_Object(-1, -1, - Target_Object_Type, - Target_Object_Instance); - /* loop forever */ - for (;;) - { - /* increment timer - exit if timed out */ - current_seconds = time(NULL); - /* returns 0 bytes on timeout */ - pdu_len = bip_receive( - &src, - &Rx_Buf[0], - MAX_MPDU, - timeout); - /* process */ - if (pdu_len) - { - npdu_handler( - &src, - &Rx_Buf[0], - pdu_len); - } - if (Error_Detected) - break; - if (I_Am_Request) - { - I_Am_Request = false; - iam_send(&Handler_Transmit_Buffer[0]); - } - else - { - /* increment timer - exit if timed out */ - elapsed_seconds += (current_seconds - last_seconds); - if (elapsed_seconds > timeout_seconds) - break; - } - /* keep track of time for next check */ - last_seconds = current_seconds; - } + BACNET_ADDRESS src = { 0 }; // address where message came from + uint16_t pdu_len = 0; + unsigned timeout = 100; // milliseconds + time_t elapsed_seconds = 0; + time_t last_seconds = 0; + time_t current_seconds = 0; + time_t timeout_seconds = 0; +#ifdef BIP_DEBUG + BACNET_ADDRESS my_address, broadcast_address; +#endif - return 0; + if (argc < 2) { + /* note: priority 16 and 0 should produce the same end results... */ + printf("Usage: %s \r\n" + "Send BACnet WhoHas request to devices, and wait for responses.\r\n" + "\r\n" + "Use either:\r\n" + "The object-type can be 0 to %d.\r\n" + "The object-instance can be 0 to %d.\r\n" + "or:\r\n" + "The object-name can be any string of characters.\r\n", + filename_remove_path(argv[0]), + MAX_BACNET_OBJECT_TYPE - 1, BACNET_MAX_INSTANCE); + return 0; + } + /* decode the command line parameters */ + if (argc < 3) { + Target_Object_Name = argv[1]; + } else { + Target_Object_Type = strtol(argv[1], NULL, 0); + Target_Object_Instance = strtol(argv[2], NULL, 0); + if (Target_Object_Instance > BACNET_MAX_INSTANCE) { + fprintf(stderr, + "object-instance=%u - it must be less than %u\r\n", + Target_Object_Instance, BACNET_MAX_INSTANCE + 1); + return 1; + } + if (Target_Object_Type > MAX_BACNET_OBJECT_TYPE) { + fprintf(stderr, "object-type=%u - it must be less than %u\r\n", + Target_Object_Type, MAX_BACNET_OBJECT_TYPE + 1); + return 1; + } + } + /* setup my info */ + Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); + Init_Service_Handlers(); + /* configure standard BACnet/IP port */ + bip_set_interface("eth0"); /* for linux */ + bip_set_port(0xBAC0); + if (!bip_init()) + return 1; +#ifdef BIP_DEBUG + datalink_get_broadcast_address(&broadcast_address); + print_address("Broadcast", &broadcast_address); + datalink_get_my_address(&my_address); + print_address("Address", &my_address); +#endif + /* configure the timeout values */ + last_seconds = time(NULL); + timeout_seconds = Device_APDU_Timeout() / 1000; + /* don't send an I-Am unless asked */ + I_Am_Request = false; + /* send the request */ + if (argc < 3) + Send_WhoHas_Name(-1, -1, Target_Object_Name); + else + Send_WhoHas_Object(-1, -1, + Target_Object_Type, Target_Object_Instance); + /* loop forever */ + for (;;) { + /* increment timer - exit if timed out */ + current_seconds = time(NULL); + /* returns 0 bytes on timeout */ + pdu_len = bip_receive(&src, &Rx_Buf[0], MAX_MPDU, timeout); + /* process */ + if (pdu_len) { + npdu_handler(&src, &Rx_Buf[0], pdu_len); + } + if (Error_Detected) + break; + if (I_Am_Request) { + I_Am_Request = false; + iam_send(&Handler_Transmit_Buffer[0]); + } else { + /* increment timer - exit if timed out */ + elapsed_seconds += (current_seconds - last_seconds); + if (elapsed_seconds > timeout_seconds) + break; + } + /* keep track of time for next check */ + last_seconds = current_seconds; + } + + return 0; } diff --git a/bacnet-stack/demo/writefile/writefile.c b/bacnet-stack/demo/writefile/writefile.c index 537f5752..5213096b 100644 --- a/bacnet-stack/demo/writefile/writefile.c +++ b/bacnet-stack/demo/writefile/writefile.c @@ -28,7 +28,7 @@ #include #include #include -#include /* for time */ +#include /* for time */ #include #include "bactext.h" #include "iam.h" @@ -49,7 +49,7 @@ #include "txbuf.h" // buffer used for receive -static uint8_t Rx_Buf[MAX_MPDU] = {0}; +static uint8_t Rx_Buf[MAX_MPDU] = { 0 }; /* global variables used in this file */ static uint32_t Target_File_Object_Instance = 4194303; @@ -60,378 +60,307 @@ static bool End_Of_File_Detected = false; static bool Error_Detected = false; static uint8_t Current_Invoke_ID = 0; -static void Atomic_Read_File_Error_Handler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - BACNET_ERROR_CLASS error_class, - BACNET_ERROR_CODE error_code) +static void Atomic_Read_File_Error_Handler(BACNET_ADDRESS * src, + uint8_t invoke_id, + BACNET_ERROR_CLASS error_class, BACNET_ERROR_CODE error_code) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("\r\nBACnet Error!\r\n"); - printf("Error Class: %s\r\n", - bactext_error_class_name(error_class)); - printf("Error Code: %s\r\n", - bactext_error_code_name(error_code)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("\r\nBACnet Error!\r\n"); + printf("Error Class: %s\r\n", bactext_error_class_name(error_class)); + printf("Error Code: %s\r\n", bactext_error_code_name(error_code)); + Error_Detected = true; } -void MyAbortHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t abort_reason) +void MyAbortHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t abort_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("\r\nBACnet Abort!\r\n"); - printf("Abort Reason: %s\r\n", - bactext_abort_reason_name(abort_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("\r\nBACnet Abort!\r\n"); + printf("Abort Reason: %s\r\n", + bactext_abort_reason_name(abort_reason)); + Error_Detected = true; } -void MyRejectHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t reject_reason) +void MyRejectHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t reject_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("\r\nBACnet Reject!\r\n"); - printf("Reject Reason: %s\r\n", - bactext_reject_reason_name(reject_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("\r\nBACnet Reject!\r\n"); + printf("Reject Reason: %s\r\n", + bactext_reject_reason_name(reject_reason)); + Error_Detected = true; } -static uint8_t Send_Atomic_Write_File_Stream( - uint32_t device_id, - uint32_t file_instance, - int fileStartPosition, - BACNET_OCTET_STRING *fileData) +static uint8_t Send_Atomic_Write_File_Stream(uint32_t device_id, + uint32_t file_instance, + int fileStartPosition, BACNET_OCTET_STRING * fileData) { - BACNET_ADDRESS dest; - BACNET_ADDRESS my_address; - unsigned max_apdu = 0; - uint8_t invoke_id = 0; - bool status = false; - int pdu_len = 0; - int bytes_sent = 0; - BACNET_ATOMIC_WRITE_FILE_DATA data; + BACNET_ADDRESS dest; + BACNET_ADDRESS my_address; + unsigned max_apdu = 0; + uint8_t invoke_id = 0; + bool status = false; + int pdu_len = 0; + int bytes_sent = 0; + BACNET_ATOMIC_WRITE_FILE_DATA data; - /* is the device bound? */ - status = address_get_by_device(device_id, &max_apdu, &dest); - /* is there a tsm available? */ - if (status) - status = tsm_transaction_available(); - if (status) - { - datalink_get_my_address(&my_address); - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - &my_address, - true, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); - - invoke_id = tsm_next_free_invokeID(); - // load the data for the encoding - data.object_type = OBJECT_FILE; - data.object_instance = file_instance; - data.access = FILE_STREAM_ACCESS; - data.type.stream.fileStartPosition = fileStartPosition; - status = octetstring_copy(&data.fileData, fileData); + /* is the device bound? */ + status = address_get_by_device(device_id, &max_apdu, &dest); + /* is there a tsm available? */ if (status) - { - pdu_len += awf_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - invoke_id, - &data); - /* will the APDU fit the target device? - note: if there is a bottleneck router in between - us and the destination, we won't know unless - we have a way to check for that and update the - max_apdu in the address binding table. */ - if ((unsigned)pdu_len <= max_apdu) - { - tsm_set_confirmed_unsegmented_transaction( - invoke_id, - &dest, - &Handler_Transmit_Buffer[0], - pdu_len); - bytes_sent = datalink_send_pdu( - &dest, // destination address - &Handler_Transmit_Buffer[0], - pdu_len); // number of bytes of data - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send AtomicWriteFile Request (%s)!\n", - strerror(errno)); - } - else - fprintf(stderr,"Failed to Send AtomicWriteFile Request " - "(payload [%d] exceeds destination maximum APDU [%u])!\n", - pdu_len,max_apdu); - } - else - fprintf(stderr,"Failed to Send AtomicWriteFile Request " - "(payload [%d] exceeds octet string capacity)!\n",pdu_len); - } + status = tsm_transaction_available(); + if (status) { + datalink_get_my_address(&my_address); + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, &my_address, true, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); - return invoke_id; + invoke_id = tsm_next_free_invokeID(); + // load the data for the encoding + data.object_type = OBJECT_FILE; + data.object_instance = file_instance; + data.access = FILE_STREAM_ACCESS; + data.type.stream.fileStartPosition = fileStartPosition; + status = octetstring_copy(&data.fileData, fileData); + if (status) { + pdu_len += awf_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + invoke_id, &data); + /* will the APDU fit the target device? + note: if there is a bottleneck router in between + us and the destination, we won't know unless + we have a way to check for that and update the + max_apdu in the address binding table. */ + if ((unsigned) pdu_len <= max_apdu) { + tsm_set_confirmed_unsegmented_transaction(invoke_id, + &dest, &Handler_Transmit_Buffer[0], pdu_len); + bytes_sent = datalink_send_pdu(&dest, // destination address + &Handler_Transmit_Buffer[0], pdu_len); // number of bytes of data + if (bytes_sent <= 0) + fprintf(stderr, + "Failed to Send AtomicWriteFile Request (%s)!\n", + strerror(errno)); + } else + fprintf(stderr, "Failed to Send AtomicWriteFile Request " + "(payload [%d] exceeds destination maximum APDU [%u])!\n", + pdu_len, max_apdu); + } else + fprintf(stderr, "Failed to Send AtomicWriteFile Request " + "(payload [%d] exceeds octet string capacity)!\n", + pdu_len); + } + + return invoke_id; } static void Send_WhoIs(uint32_t device_id) { - int pdu_len = 0; - BACNET_ADDRESS dest; - int bytes_sent = 0; + int pdu_len = 0; + BACNET_ADDRESS dest; + int bytes_sent = 0; - /* Who-Is is a global broadcast */ - datalink_get_broadcast_address(&dest); + /* Who-Is is a global broadcast */ + datalink_get_broadcast_address(&dest); - /* encode the NPDU portion of the packet */ - pdu_len = npdu_encode_apdu( - &Handler_Transmit_Buffer[0], - &dest, - NULL, - false, // true for confirmed messages - MESSAGE_PRIORITY_NORMAL); + /* encode the NPDU portion of the packet */ + pdu_len = npdu_encode_apdu(&Handler_Transmit_Buffer[0], &dest, NULL, false, // true for confirmed messages + MESSAGE_PRIORITY_NORMAL); - /* encode the APDU portion of the packet */ - pdu_len += whois_encode_apdu( - &Handler_Transmit_Buffer[pdu_len], - device_id, - device_id); + /* encode the APDU portion of the packet */ + pdu_len += whois_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + device_id, device_id); - bytes_sent = datalink_send_pdu( - &dest, /* destination address */ - &Handler_Transmit_Buffer[0], - pdu_len); /* number of bytes of data */ - if (bytes_sent <= 0) - fprintf(stderr,"Failed to Send Who-Is Request (%s)!\n", strerror(errno)); + bytes_sent = datalink_send_pdu(&dest, /* destination address */ + &Handler_Transmit_Buffer[0], pdu_len); /* number of bytes of data */ + if (bytes_sent <= 0) + fprintf(stderr, "Failed to Send Who-Is Request (%s)!\n", + strerror(errno)); } -static void LocalIAmHandler( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src) +static void LocalIAmHandler(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src) { - int len = 0; - uint32_t device_id = 0; - unsigned max_apdu = 0; - int segmentation = 0; - uint16_t vendor_id = 0; + int len = 0; + uint32_t device_id = 0; + unsigned max_apdu = 0; + int segmentation = 0; + uint16_t vendor_id = 0; - (void)src; - (void)service_len; - len = iam_decode_service_request( - service_request, - &device_id, - &max_apdu, - &segmentation, - &vendor_id); - if (len != -1) - { - address_add(device_id, - max_apdu, - src); - } - else - fprintf(stderr,"!\n"); + (void) src; + (void) service_len; + len = iam_decode_service_request(service_request, + &device_id, &max_apdu, &segmentation, &vendor_id); + if (len != -1) { + address_add(device_id, max_apdu, src); + } else + fprintf(stderr, "!\n"); - return; + return; } static void Init_Service_Handlers(void) { - /* we need to handle who-is - to support dynamic device binding to us */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_WHO_IS, - handler_who_is); - /* handle i-am to support binding to other devices */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_I_AM, - LocalIAmHandler); - /* set the handler for all the services we don't implement - It is required to send the proper reject message... */ - apdu_set_unrecognized_service_handler_handler( - handler_unrecognized_service); - /* we must implement read property - it's required! */ - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property); - /* handle any errors coming back */ - apdu_set_error_handler( - SERVICE_CONFIRMED_ATOMIC_READ_FILE, - Atomic_Read_File_Error_Handler); - apdu_set_abort_handler( - MyAbortHandler); - apdu_set_reject_handler( - MyRejectHandler); + /* we need to handle who-is + to support dynamic device binding to us */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_WHO_IS, + handler_who_is); + /* handle i-am to support binding to other devices */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_I_AM, + LocalIAmHandler); + /* set the handler for all the services we don't implement + It is required to send the proper reject message... */ + apdu_set_unrecognized_service_handler_handler + (handler_unrecognized_service); + /* we must implement read property - it's required! */ + apdu_set_confirmed_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property); + /* handle any errors coming back */ + apdu_set_error_handler(SERVICE_CONFIRMED_ATOMIC_READ_FILE, + Atomic_Read_File_Error_Handler); + apdu_set_abort_handler(MyAbortHandler); + apdu_set_reject_handler(MyRejectHandler); } int main(int argc, char *argv[]) { - BACNET_ADDRESS src = {0}; // address where message came from - uint16_t pdu_len = 0; - unsigned timeout = 100; // milliseconds - unsigned max_apdu = 0; - time_t elapsed_seconds = 0; - time_t last_seconds = 0; - time_t current_seconds = 0; - time_t timeout_seconds = 0; - int fileStartPosition = 0; - unsigned requestedOctetCount = 0; - uint8_t invoke_id = 0; - bool found = false; - uint16_t my_max_apdu = 0; - FILE *pFile = NULL; - static BACNET_OCTET_STRING fileData; - size_t len = 0; - - if (argc < 4) - { - /* FIXME: what about access method - record or stream? */ - printf("%s device-instance file-instance local-name\r\n", - filename_remove_path(argv[0])); - return 0; - } - /* decode the command line parameters */ - Target_Device_Object_Instance = strtol(argv[1],NULL,0); - Target_File_Object_Instance = strtol(argv[2],NULL,0); - Local_File_Name = argv[3]; - if (Target_Device_Object_Instance >= BACNET_MAX_INSTANCE) - { - fprintf(stderr,"device-instance=%u - it must be less than %u\r\n", - Target_Device_Object_Instance,BACNET_MAX_INSTANCE); - return 1; - } - if (Target_File_Object_Instance >= BACNET_MAX_INSTANCE) - { - fprintf(stderr,"file-instance=%u - it must be less than %u\r\n", - Target_File_Object_Instance,BACNET_MAX_INSTANCE+1); - return 1; - } - /* setup my info */ - Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); - address_init(); - Init_Service_Handlers(); - /* configure standard BACnet/IP port */ - bip_set_interface("eth0"); /* for linux */ - bip_set_port(0xBAC0); - if (!bip_init()) - return 1; - /* configure the timeout values */ - last_seconds = time(NULL); - timeout_seconds = (Device_APDU_Timeout() / 1000) * - Device_Number_Of_APDU_Retries(); - /* try to bind with the device */ - Send_WhoIs(Target_Device_Object_Instance); - /* loop forever */ - for (;;) - { - /* increment timer - exit if timed out */ - current_seconds = time(NULL); + BACNET_ADDRESS src = { 0 }; // address where message came from + uint16_t pdu_len = 0; + unsigned timeout = 100; // milliseconds + unsigned max_apdu = 0; + time_t elapsed_seconds = 0; + time_t last_seconds = 0; + time_t current_seconds = 0; + time_t timeout_seconds = 0; + int fileStartPosition = 0; + unsigned requestedOctetCount = 0; + uint8_t invoke_id = 0; + bool found = false; + uint16_t my_max_apdu = 0; + FILE *pFile = NULL; + static BACNET_OCTET_STRING fileData; + size_t len = 0; - /* returns 0 bytes on timeout */ - pdu_len = bip_receive( - &src, - &Rx_Buf[0], - MAX_MPDU, - timeout); - - /* process */ - if (pdu_len) - { - npdu_handler( - &src, - &Rx_Buf[0], - pdu_len); + if (argc < 4) { + /* FIXME: what about access method - record or stream? */ + printf("%s device-instance file-instance local-name\r\n", + filename_remove_path(argv[0])); + return 0; } - /* at least one second has passed */ - if (current_seconds != last_seconds) - tsm_timer_milliseconds(((current_seconds - last_seconds) * 1000)); - if (End_Of_File_Detected || Error_Detected) - { - printf("\r\n"); - break; + /* decode the command line parameters */ + Target_Device_Object_Instance = strtol(argv[1], NULL, 0); + Target_File_Object_Instance = strtol(argv[2], NULL, 0); + Local_File_Name = argv[3]; + if (Target_Device_Object_Instance >= BACNET_MAX_INSTANCE) { + fprintf(stderr, "device-instance=%u - it must be less than %u\r\n", + Target_Device_Object_Instance, BACNET_MAX_INSTANCE); + return 1; } - if (I_Am_Request) - { - I_Am_Request = false; - iam_send(&Handler_Transmit_Buffer[0]); + if (Target_File_Object_Instance >= BACNET_MAX_INSTANCE) { + fprintf(stderr, "file-instance=%u - it must be less than %u\r\n", + Target_File_Object_Instance, BACNET_MAX_INSTANCE + 1); + return 1; } - else - { - /* wait until the device is bound, or timeout and quit */ - found = address_bind_request( - Target_Device_Object_Instance, - &max_apdu, - &Target_Address); - if (found) - { - /* calculate the smaller of our APDU size or theirs - and remove the overhead of the APDU (varies depending on size). - note: we could fail if there is a bottle neck (router) - and smaller MPDU in betweeen. */ - if (max_apdu < MAX_APDU) - my_max_apdu = max_apdu; - else - my_max_apdu = MAX_APDU; - /* Typical sizes are 50, 128, 206, 480, 1024, and 1476 octets */ - if (my_max_apdu <= 50) - requestedOctetCount = my_max_apdu - 16; - else if (my_max_apdu <= 480) - requestedOctetCount = my_max_apdu - 32; - else if (my_max_apdu <= 1476) - requestedOctetCount = my_max_apdu - 64; - else - requestedOctetCount = my_max_apdu / 2; - /* has the previous invoke id expired or returned? - note: invoke ID = 0 is invalid, so it will be idle */ - if ((invoke_id == 0) || tsm_invoke_id_free(invoke_id)) - { - if (invoke_id != 0) - fileStartPosition += requestedOctetCount; - /* we'll read the file in chunks - less than max_apdu to keep unsegmented */ - pFile = fopen(Local_File_Name,"rb"); - if (pFile) - { - (void)fseek(pFile, - fileStartPosition, - SEEK_SET); - len = fread(octetstring_value(&fileData), 1, - requestedOctetCount, pFile); - if (len < requestedOctetCount) - End_Of_File_Detected = true; - octetstring_truncate(&fileData,len); - fclose(pFile); - } - else - End_Of_File_Detected = true; - printf("\rSending %d bytes",(fileStartPosition+len)); - invoke_id = Send_Atomic_Write_File_Stream( - Target_Device_Object_Instance, - Target_File_Object_Instance, - fileStartPosition, - &fileData); - Current_Invoke_ID = invoke_id; - } - } - else - { + /* setup my info */ + Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); + address_init(); + Init_Service_Handlers(); + /* configure standard BACnet/IP port */ + bip_set_interface("eth0"); /* for linux */ + bip_set_port(0xBAC0); + if (!bip_init()) + return 1; + /* configure the timeout values */ + last_seconds = time(NULL); + timeout_seconds = (Device_APDU_Timeout() / 1000) * + Device_Number_Of_APDU_Retries(); + /* try to bind with the device */ + Send_WhoIs(Target_Device_Object_Instance); + /* loop forever */ + for (;;) { /* increment timer - exit if timed out */ - elapsed_seconds += (current_seconds - last_seconds); - if (elapsed_seconds > timeout_seconds) - break; - } - } - /* keep track of time for next check */ - last_seconds = current_seconds; - } + current_seconds = time(NULL); - return 0; + /* returns 0 bytes on timeout */ + pdu_len = bip_receive(&src, &Rx_Buf[0], MAX_MPDU, timeout); + + /* process */ + if (pdu_len) { + npdu_handler(&src, &Rx_Buf[0], pdu_len); + } + /* at least one second has passed */ + if (current_seconds != last_seconds) + tsm_timer_milliseconds(((current_seconds - + last_seconds) * 1000)); + if (End_Of_File_Detected || Error_Detected) { + printf("\r\n"); + break; + } + if (I_Am_Request) { + I_Am_Request = false; + iam_send(&Handler_Transmit_Buffer[0]); + } else { + /* wait until the device is bound, or timeout and quit */ + found = address_bind_request(Target_Device_Object_Instance, + &max_apdu, &Target_Address); + if (found) { + /* calculate the smaller of our APDU size or theirs + and remove the overhead of the APDU (varies depending on size). + note: we could fail if there is a bottle neck (router) + and smaller MPDU in betweeen. */ + if (max_apdu < MAX_APDU) + my_max_apdu = max_apdu; + else + my_max_apdu = MAX_APDU; + /* Typical sizes are 50, 128, 206, 480, 1024, and 1476 octets */ + if (my_max_apdu <= 50) + requestedOctetCount = my_max_apdu - 16; + else if (my_max_apdu <= 480) + requestedOctetCount = my_max_apdu - 32; + else if (my_max_apdu <= 1476) + requestedOctetCount = my_max_apdu - 64; + else + requestedOctetCount = my_max_apdu / 2; + /* has the previous invoke id expired or returned? + note: invoke ID = 0 is invalid, so it will be idle */ + if ((invoke_id == 0) || tsm_invoke_id_free(invoke_id)) { + if (invoke_id != 0) + fileStartPosition += requestedOctetCount; + /* we'll read the file in chunks + less than max_apdu to keep unsegmented */ + pFile = fopen(Local_File_Name, "rb"); + if (pFile) { + (void) fseek(pFile, fileStartPosition, SEEK_SET); + len = fread(octetstring_value(&fileData), 1, + requestedOctetCount, pFile); + if (len < requestedOctetCount) + End_Of_File_Detected = true; + octetstring_truncate(&fileData, len); + fclose(pFile); + } else + End_Of_File_Detected = true; + printf("\rSending %d bytes", + (fileStartPosition + len)); + invoke_id = + Send_Atomic_Write_File_Stream + (Target_Device_Object_Instance, + Target_File_Object_Instance, fileStartPosition, + &fileData); + Current_Invoke_ID = invoke_id; + } + } else { + /* increment timer - exit if timed out */ + elapsed_seconds += (current_seconds - last_seconds); + if (elapsed_seconds > timeout_seconds) + break; + } + } + /* keep track of time for next check */ + last_seconds = current_seconds; + } + + return 0; } diff --git a/bacnet-stack/demo/writeprop/writeprop.c b/bacnet-stack/demo/writeprop/writeprop.c index 8ca2a5da..00e60716 100644 --- a/bacnet-stack/demo/writeprop/writeprop.c +++ b/bacnet-stack/demo/writeprop/writeprop.c @@ -28,7 +28,7 @@ #include #include #include -#include /* for time */ +#include /* for time */ #include #include "bactext.h" #include "iam.h" @@ -50,7 +50,7 @@ #include "txbuf.h" // buffer used for receive -static uint8_t Rx_Buf[MAX_MPDU] = {0}; +static uint8_t Rx_Buf[MAX_MPDU] = { 0 }; /* global variables used in this file */ static uint32_t Target_Device_Object_Instance = BACNET_MAX_INSTANCE; @@ -59,326 +59,284 @@ static BACNET_OBJECT_TYPE Target_Object_Type = OBJECT_ANALOG_INPUT; static BACNET_PROPERTY_ID Target_Object_Property = PROP_ACKED_TRANSITIONS; /* array index value or BACNET_ARRAY_ALL */ static int32_t Target_Object_Property_Index = BACNET_ARRAY_ALL; -static BACNET_APPLICATION_TAG Target_Object_Property_Tag = BACNET_APPLICATION_TAG_NULL; -static BACNET_APPLICATION_DATA_VALUE Target_Object_Property_Value = {0}; +static BACNET_APPLICATION_TAG Target_Object_Property_Tag = + BACNET_APPLICATION_TAG_NULL; +static BACNET_APPLICATION_DATA_VALUE Target_Object_Property_Value = { 0 }; + /* 0 if not set, 1..16 if set */ static uint8_t Target_Object_Property_Priority = 0; static BACNET_ADDRESS Target_Address; static bool Error_Detected = false; -static void MyErrorHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - BACNET_ERROR_CLASS error_class, - BACNET_ERROR_CODE error_code) +static void MyErrorHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, + BACNET_ERROR_CLASS error_class, BACNET_ERROR_CODE error_code) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("\r\nBACnet Error!\r\n"); - printf("Error Class: %s\r\n", - bactext_error_class_name(error_class)); - printf("Error Code: %s\r\n", - bactext_error_code_name(error_code)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("\r\nBACnet Error!\r\n"); + printf("Error Class: %s\r\n", bactext_error_class_name(error_class)); + printf("Error Code: %s\r\n", bactext_error_code_name(error_code)); + Error_Detected = true; } -void MyAbortHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t abort_reason) +void MyAbortHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t abort_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("\r\nBACnet Abort!\r\n"); - printf("Abort Reason: %s\r\n", - bactext_abort_reason_name(abort_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("\r\nBACnet Abort!\r\n"); + printf("Abort Reason: %s\r\n", + bactext_abort_reason_name(abort_reason)); + Error_Detected = true; } -void MyRejectHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id, - uint8_t reject_reason) +void MyRejectHandler(BACNET_ADDRESS * src, + uint8_t invoke_id, uint8_t reject_reason) { - /* FIXME: verify src and invoke id */ - (void)src; - (void)invoke_id; - printf("\r\nBACnet Reject!\r\n"); - printf("Reject Reason: %s\r\n", - bactext_reject_reason_name(reject_reason)); - Error_Detected = true; + /* FIXME: verify src and invoke id */ + (void) src; + (void) invoke_id; + printf("\r\nBACnet Reject!\r\n"); + printf("Reject Reason: %s\r\n", + bactext_reject_reason_name(reject_reason)); + Error_Detected = true; } -void MyWritePropertySimpleAckHandler( - BACNET_ADDRESS *src, - uint8_t invoke_id) +void MyWritePropertySimpleAckHandler(BACNET_ADDRESS * src, + uint8_t invoke_id) { - (void)src; - (void)invoke_id; - printf("\r\nWriteProperty Acknowledged!\r\n"); + (void) src; + (void) invoke_id; + printf("\r\nWriteProperty Acknowledged!\r\n"); } static void Init_Service_Handlers(void) { - /* we need to handle who-is - to support dynamic device binding to us */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_WHO_IS, - handler_who_is); - /* handle i-am to support binding to other devices */ - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_I_AM, - handler_i_am_bind); - /* set the handler for all the services we don't implement - It is required to send the proper reject message... */ - apdu_set_unrecognized_service_handler_handler( - handler_unrecognized_service); - /* we must implement read property - it's required! */ - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property); - /* handle the ack coming back */ - apdu_set_confirmed_simple_ack_handler( - SERVICE_CONFIRMED_WRITE_PROPERTY, - MyWritePropertySimpleAckHandler); - /* handle any errors coming back */ - apdu_set_error_handler( - SERVICE_CONFIRMED_WRITE_PROPERTY, - MyErrorHandler); - apdu_set_abort_handler( - MyAbortHandler); - apdu_set_reject_handler( - MyRejectHandler); + /* we need to handle who-is + to support dynamic device binding to us */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_WHO_IS, + handler_who_is); + /* handle i-am to support binding to other devices */ + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_I_AM, + handler_i_am_bind); + /* set the handler for all the services we don't implement + It is required to send the proper reject message... */ + apdu_set_unrecognized_service_handler_handler + (handler_unrecognized_service); + /* we must implement read property - it's required! */ + apdu_set_confirmed_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property); + /* handle the ack coming back */ + apdu_set_confirmed_simple_ack_handler(SERVICE_CONFIRMED_WRITE_PROPERTY, + MyWritePropertySimpleAckHandler); + /* handle any errors coming back */ + apdu_set_error_handler(SERVICE_CONFIRMED_WRITE_PROPERTY, + MyErrorHandler); + apdu_set_abort_handler(MyAbortHandler); + apdu_set_reject_handler(MyRejectHandler); } int main(int argc, char *argv[]) { - BACNET_ADDRESS src = {0}; // address where message came from - uint16_t pdu_len = 0; - unsigned timeout = 100; // milliseconds - unsigned max_apdu = 0; - time_t elapsed_seconds = 0; - time_t last_seconds = 0; - time_t current_seconds = 0; - time_t timeout_seconds = 0; - uint8_t invoke_id = 0; - bool found = false; - char *value_string = NULL; - bool status = false; - - if (argc < 7) - { - /* note: priority 16 and 0 should produce the same end results... */ - printf("Usage: %s device-instance object-type object-instance " - "property tag value [priority] [index]\r\n" - "\r\n" - "device-instance:\r\n" - "BACnet Device Object Instance number that you are trying to\r\n" - "communicate to. This number will be used to try and bind with\r\n" - "the device using Who-Is and I-Am services. For example, if you were\r\n" - "writing to Device Object 123, the device-instance would be 123.\r\n" - "\r\n" - "object-type:\r\n" - "The object type is the integer value of the enumeration\r\n" - "BACNET_OBJECT_TYPE in bacenum.h. It is the object that you are\r\n" - "writing to. For example if you were writing to Analog Output 2, \r\n" - "the object-type would be 1.\r\n" - "\r\n" - "object-instance:\r\n" - "This is the object instance number of the object that you are \r\n" - "writing to. For example, if you were writing to Analog Output 2, \r\n" - "the object-instance would be 2.\r\n" - "\r\n" - "property:\r\n" - "The property is an integer value of the enumeration \r\n" - "BACNET_PROPERTY_ID in bacenum.h. It is the property you are \r\n" - "writing to. For example, if you were writing to the Present Value\r\n" - "property, you would use 85 as the property.\r\n" - "\r\n" - "tag:\r\n" - "Tag is the integer value of the enumeration BACNET_APPLICATION_TAG \r\n" - "in bacenum.h. It is the data type of the value that you are\r\n" - "writing. For example, if you were writing a REAL value, you would \r\n" - "use a tag of 4." - "\r\n" - "value:\r\n" - "The value is an ASCII representation of some type of data that you\r\n" - "are writing. It is encoded using the tag information provided. For\r\n" - "example, if you were writing a REAL value of 100.0, you would use \r\n" - "100.0 as the value.\r\n" - "\r\n" - "[priority]:\r\n" - "This optional parameter is used for setting the priority of the\r\n" - "write. If no priority is given, none is sent, and the BACnet \r\n" - "standard requires that the value is written at the lowest \r\n" - "priority (16) if the object property supports priorities.\r\n" - "\r\n" - "[index]\r\n" - "This optional integer parameter is the index number of an array.\r\n" - "If the property is an array, individual elements can be written\r\n" - "to if supported.\r\n" - "\r\n" - "Here is a brief overview of BACnet property and tags:\r\n" - "Certain properties are expected to be written with certain \r\n" - "application tags, so you probably need to know which ones to use\r\n" - "with each property of each object. It is almost safe to say that\r\n" - "given a property and an object and a table, the tag could be looked\r\n" - "up automatically. There may be a few exceptions to this, such as\r\n" - "the Any property type in the schedule object and the Present Value\r\n" - "accepting REAL, BOOLEAN, NULL, etc. Perhaps it would be simpler for\r\n" - "the demo to use this kind of table - but I also wanted to be able\r\n" - "to do negative testing by passing the wrong tag and have the server\r\n" - "return a reject message.\r\n" - "\r\n" - "Example:\r\n" - "If you want send a 100 to the Present-Value in the Analog Output\r\n" - "at priority 16, you could send the following command:\r\n" - "%s 123 1 0 85 4 100\r\n" - "You could also send a relinquish command:\r\n" - "%s 123 1 0 85 0 0\r\n", - filename_remove_path(argv[0]), - filename_remove_path(argv[0]), - filename_remove_path(argv[0])); - return 0; - } - /* decode the command line parameters */ - Target_Device_Object_Instance = strtol(argv[1],NULL,0); - Target_Object_Type = strtol(argv[2],NULL,0); - Target_Object_Instance = strtol(argv[3],NULL,0); - Target_Object_Property = strtol(argv[4],NULL,0); - Target_Object_Property_Tag = strtol(argv[5],NULL,0); - value_string = argv[6]; - /* optional priority */ - if (argc > 7) - Target_Object_Property_Priority = strtol(argv[7],NULL,0); - /* optional index */ - if (argc > 8) - Target_Object_Property_Index = strtol(argv[8],NULL,0); - - if (Target_Device_Object_Instance >= BACNET_MAX_INSTANCE) - { - fprintf(stderr,"device-instance=%u - it must be less than %u\r\n", - Target_Device_Object_Instance,BACNET_MAX_INSTANCE); - return 1; - } - if (Target_Object_Type > MAX_BACNET_OBJECT_TYPE) - { - fprintf(stderr,"object-type=%u - it must be less than %u\r\n", - Target_Object_Type,MAX_BACNET_OBJECT_TYPE+1); - return 1; - } - if (Target_Object_Instance > BACNET_MAX_INSTANCE) - { - fprintf(stderr,"object-instance=%u - it must be less than %u\r\n", - Target_Object_Instance,BACNET_MAX_INSTANCE+1); - return 1; - } - if (Target_Object_Property > MAX_BACNET_PROPERTY_ID) - { - fprintf(stderr,"object-type=%u - it must be less than %u\r\n", - Target_Object_Property,MAX_BACNET_PROPERTY_ID+1); - return 1; - } - if (Target_Object_Property_Tag >= MAX_BACNET_APPLICATION_TAG) - { - fprintf(stderr,"tag=%u - it must be less than %u\r\n", - Target_Object_Property_Tag,MAX_BACNET_APPLICATION_TAG); - return 1; - } - status = bacapp_parse_application_data( - Target_Object_Property_Tag, - value_string, - &Target_Object_Property_Value); - if (!status) - { - /* FIXME: show the expected entry format for the tag */ - fprintf(stderr,"unable to parse the tag value\r\n"); - return 1; - } - - /* setup my info */ - Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); - address_init(); - Init_Service_Handlers(); - /* configure standard BACnet/IP port */ - bip_set_interface("eth0"); /* for linux */ - bip_set_port(0xBAC0); - if (!bip_init()) - return 1; - /* configure the timeout values */ - last_seconds = time(NULL); - timeout_seconds = (Device_APDU_Timeout() / 1000) * - Device_Number_Of_APDU_Retries(); - /* try to bind with the device */ - Send_WhoIs(Target_Device_Object_Instance,Target_Device_Object_Instance); - /* loop forever */ - for (;;) - { - /* increment timer - exit if timed out */ - current_seconds = time(NULL); + BACNET_ADDRESS src = { 0 }; // address where message came from + uint16_t pdu_len = 0; + unsigned timeout = 100; // milliseconds + unsigned max_apdu = 0; + time_t elapsed_seconds = 0; + time_t last_seconds = 0; + time_t current_seconds = 0; + time_t timeout_seconds = 0; + uint8_t invoke_id = 0; + bool found = false; + char *value_string = NULL; + bool status = false; - /* returns 0 bytes on timeout */ - pdu_len = bip_receive( - &src, - &Rx_Buf[0], - MAX_MPDU, - timeout); + if (argc < 7) { + /* note: priority 16 and 0 should produce the same end results... */ + printf("Usage: %s device-instance object-type object-instance " + "property tag value [priority] [index]\r\n" + "\r\n" + "device-instance:\r\n" + "BACnet Device Object Instance number that you are trying to\r\n" + "communicate to. This number will be used to try and bind with\r\n" + "the device using Who-Is and I-Am services. For example, if you were\r\n" + "writing to Device Object 123, the device-instance would be 123.\r\n" + "\r\n" + "object-type:\r\n" + "The object type is the integer value of the enumeration\r\n" + "BACNET_OBJECT_TYPE in bacenum.h. It is the object that you are\r\n" + "writing to. For example if you were writing to Analog Output 2, \r\n" + "the object-type would be 1.\r\n" + "\r\n" + "object-instance:\r\n" + "This is the object instance number of the object that you are \r\n" + "writing to. For example, if you were writing to Analog Output 2, \r\n" + "the object-instance would be 2.\r\n" + "\r\n" + "property:\r\n" + "The property is an integer value of the enumeration \r\n" + "BACNET_PROPERTY_ID in bacenum.h. It is the property you are \r\n" + "writing to. For example, if you were writing to the Present Value\r\n" + "property, you would use 85 as the property.\r\n" + "\r\n" + "tag:\r\n" + "Tag is the integer value of the enumeration BACNET_APPLICATION_TAG \r\n" + "in bacenum.h. It is the data type of the value that you are\r\n" + "writing. For example, if you were writing a REAL value, you would \r\n" + "use a tag of 4." + "\r\n" + "value:\r\n" + "The value is an ASCII representation of some type of data that you\r\n" + "are writing. It is encoded using the tag information provided. For\r\n" + "example, if you were writing a REAL value of 100.0, you would use \r\n" + "100.0 as the value.\r\n" + "\r\n" + "[priority]:\r\n" + "This optional parameter is used for setting the priority of the\r\n" + "write. If no priority is given, none is sent, and the BACnet \r\n" + "standard requires that the value is written at the lowest \r\n" + "priority (16) if the object property supports priorities.\r\n" + "\r\n" + "[index]\r\n" + "This optional integer parameter is the index number of an array.\r\n" + "If the property is an array, individual elements can be written\r\n" + "to if supported.\r\n" + "\r\n" + "Here is a brief overview of BACnet property and tags:\r\n" + "Certain properties are expected to be written with certain \r\n" + "application tags, so you probably need to know which ones to use\r\n" + "with each property of each object. It is almost safe to say that\r\n" + "given a property and an object and a table, the tag could be looked\r\n" + "up automatically. There may be a few exceptions to this, such as\r\n" + "the Any property type in the schedule object and the Present Value\r\n" + "accepting REAL, BOOLEAN, NULL, etc. Perhaps it would be simpler for\r\n" + "the demo to use this kind of table - but I also wanted to be able\r\n" + "to do negative testing by passing the wrong tag and have the server\r\n" + "return a reject message.\r\n" + "\r\n" + "Example:\r\n" + "If you want send a 100 to the Present-Value in the Analog Output\r\n" + "at priority 16, you could send the following command:\r\n" + "%s 123 1 0 85 4 100\r\n" + "You could also send a relinquish command:\r\n" + "%s 123 1 0 85 0 0\r\n", + filename_remove_path(argv[0]), + filename_remove_path(argv[0]), filename_remove_path(argv[0])); + return 0; + } + /* decode the command line parameters */ + Target_Device_Object_Instance = strtol(argv[1], NULL, 0); + Target_Object_Type = strtol(argv[2], NULL, 0); + Target_Object_Instance = strtol(argv[3], NULL, 0); + Target_Object_Property = strtol(argv[4], NULL, 0); + Target_Object_Property_Tag = strtol(argv[5], NULL, 0); + value_string = argv[6]; + /* optional priority */ + if (argc > 7) + Target_Object_Property_Priority = strtol(argv[7], NULL, 0); + /* optional index */ + if (argc > 8) + Target_Object_Property_Index = strtol(argv[8], NULL, 0); - /* process */ - if (pdu_len) - { - npdu_handler( - &src, - &Rx_Buf[0], - pdu_len); + if (Target_Device_Object_Instance >= BACNET_MAX_INSTANCE) { + fprintf(stderr, "device-instance=%u - it must be less than %u\r\n", + Target_Device_Object_Instance, BACNET_MAX_INSTANCE); + return 1; } - /* at least one second has passed */ - if (current_seconds != last_seconds) - tsm_timer_milliseconds(((current_seconds - last_seconds) * 1000)); - if (Error_Detected) - break; - if (I_Am_Request) - { - I_Am_Request = false; - iam_send(&Handler_Transmit_Buffer[0]); + if (Target_Object_Type > MAX_BACNET_OBJECT_TYPE) { + fprintf(stderr, "object-type=%u - it must be less than %u\r\n", + Target_Object_Type, MAX_BACNET_OBJECT_TYPE + 1); + return 1; } - else - { - /* wait until the device is bound, or timeout and quit */ - found = address_bind_request( - Target_Device_Object_Instance, - &max_apdu, - &Target_Address); - if (found) - { - if (invoke_id == 0) - { - invoke_id = Send_Write_Property_Request( - Target_Device_Object_Instance, - Target_Object_Type, - Target_Object_Instance, - Target_Object_Property, - &Target_Object_Property_Value, - Target_Object_Property_Priority, - Target_Object_Property_Index); - } - else if (tsm_invoke_id_free(invoke_id)) - break; - } - else - { + if (Target_Object_Instance > BACNET_MAX_INSTANCE) { + fprintf(stderr, "object-instance=%u - it must be less than %u\r\n", + Target_Object_Instance, BACNET_MAX_INSTANCE + 1); + return 1; + } + if (Target_Object_Property > MAX_BACNET_PROPERTY_ID) { + fprintf(stderr, "object-type=%u - it must be less than %u\r\n", + Target_Object_Property, MAX_BACNET_PROPERTY_ID + 1); + return 1; + } + if (Target_Object_Property_Tag >= MAX_BACNET_APPLICATION_TAG) { + fprintf(stderr, "tag=%u - it must be less than %u\r\n", + Target_Object_Property_Tag, MAX_BACNET_APPLICATION_TAG); + return 1; + } + status = bacapp_parse_application_data(Target_Object_Property_Tag, + value_string, &Target_Object_Property_Value); + if (!status) { + /* FIXME: show the expected entry format for the tag */ + fprintf(stderr, "unable to parse the tag value\r\n"); + return 1; + } + + /* setup my info */ + Device_Set_Object_Instance_Number(BACNET_MAX_INSTANCE); + address_init(); + Init_Service_Handlers(); + /* configure standard BACnet/IP port */ + bip_set_interface("eth0"); /* for linux */ + bip_set_port(0xBAC0); + if (!bip_init()) + return 1; + /* configure the timeout values */ + last_seconds = time(NULL); + timeout_seconds = (Device_APDU_Timeout() / 1000) * + Device_Number_Of_APDU_Retries(); + /* try to bind with the device */ + Send_WhoIs(Target_Device_Object_Instance, + Target_Device_Object_Instance); + /* loop forever */ + for (;;) { /* increment timer - exit if timed out */ - elapsed_seconds += (current_seconds - last_seconds); - if (elapsed_seconds > timeout_seconds) - break; - } - } - /* keep track of time for next check */ - last_seconds = current_seconds; - } + current_seconds = time(NULL); - return 0; + /* returns 0 bytes on timeout */ + pdu_len = bip_receive(&src, &Rx_Buf[0], MAX_MPDU, timeout); + + /* process */ + if (pdu_len) { + npdu_handler(&src, &Rx_Buf[0], pdu_len); + } + /* at least one second has passed */ + if (current_seconds != last_seconds) + tsm_timer_milliseconds(((current_seconds - + last_seconds) * 1000)); + if (Error_Detected) + break; + if (I_Am_Request) { + I_Am_Request = false; + iam_send(&Handler_Transmit_Buffer[0]); + } else { + /* wait until the device is bound, or timeout and quit */ + found = address_bind_request(Target_Device_Object_Instance, + &max_apdu, &Target_Address); + if (found) { + if (invoke_id == 0) { + invoke_id = + Send_Write_Property_Request + (Target_Device_Object_Instance, Target_Object_Type, + Target_Object_Instance, Target_Object_Property, + &Target_Object_Property_Value, + Target_Object_Property_Priority, + Target_Object_Property_Index); + } else if (tsm_invoke_id_free(invoke_id)) + break; + } else { + /* increment timer - exit if timed out */ + elapsed_seconds += (current_seconds - last_seconds); + if (elapsed_seconds > timeout_seconds) + break; + } + } + /* keep track of time for next check */ + last_seconds = current_seconds; + } + + return 0; } diff --git a/bacnet-stack/doc/code-standard.txt b/bacnet-stack/doc/code-standard.txt index 749c9776..8b9720e0 100644 --- a/bacnet-stack/doc/code-standard.txt +++ b/bacnet-stack/doc/code-standard.txt @@ -6,7 +6,9 @@ Don't use C++-style comments (comments beginning with "//" and running to the end of the line) for modules that are written in C. The module may run through C rather than C++ compilers, and not all C compilers support C++-style comments (GCC does, but IBM's C compiler for AIX, for -example, doesn't do so by default). +example, doesn't do so by default). Note: there is a program +called usr/bin/ccmtcnvt in the liwc package that converts the C++ +comments to C comments. Don't initialize variables in their declaration with non-constant values. Not all compilers support this. E.g. don't use diff --git a/bacnet-stack/mstp.c b/bacnet-stack/mstp.c index 52c5fd84..35ced47a 100644 --- a/bacnet-stack/mstp.c +++ b/bacnet-stack/mstp.c @@ -576,8 +576,7 @@ void MSTP_Master_Node_FSM(volatile struct mstp_port_struct_t *mstp_port) // that is not known to this node. // FIXME: change this if you add a proprietary type else if /*( */ (mstp_port->FrameType >= - FRAME_TYPE_PROPRIETARY_MIN) - { /*&& */ + FRAME_TYPE_PROPRIETARY_MIN) { /*&& */ /*(FrameType <= FRAME_TYPE_PROPRIETARY_MAX)) */ /* unnecessary if FrameType is uint8_t with max of 255 */ // an unexpected or unwanted frame was received. diff --git a/bacnet-stack/ports/linux/arcnet.c b/bacnet-stack/ports/linux/arcnet.c index ab8991e1..eafcd3a1 100644 --- a/bacnet-stack/ports/linux/arcnet.c +++ b/bacnet-stack/ports/linux/arcnet.c @@ -40,7 +40,7 @@ // my local device data - MAC address uint8_t ARCNET_MAC_Address = 0; // ARCNET file handle -static int ARCNET_Sock_FD = -1; +static int ARCNET_Sock_FD = -1; // ARCNET socket address (has the interface name) static struct sockaddr ARCNET_Socket_Address; // Broadcast address @@ -81,206 +81,192 @@ clockp Clock Prescaler DataRate bool arcnet_valid(void) { - return (ARCNET_Sock_FD >= 0); + return (ARCNET_Sock_FD >= 0); } void arcnet_cleanup(void) { - if (arcnet_valid()) - close(ARCNET_Sock_FD); - ARCNET_Sock_FD = -1; + if (arcnet_valid()) + close(ARCNET_Sock_FD); + ARCNET_Sock_FD = -1; - return; + return; } static int arcnet_bind(char *interface_name) { - int sock_fd = -1; // return value - struct ifreq ifr; - int rv; // return value - error value from df or ioctl call - int uid = 0; + int sock_fd = -1; // return value + struct ifreq ifr; + int rv; // return value - error value from df or ioctl call + int uid = 0; - /* check to see if we are being run as root */ - uid = getuid(); - if (uid != 0) { - fprintf(stderr, - "arcnet: Unable to open an af_packet socket. " - "Try running with root priveleges.\n"); - return sock_fd; - } - fprintf(stderr,"arcnet: opening \"%s\"\n",interface_name); - // note: on some systems you may have to add or enable in - // modules.conf (or in modutils/alias on Debian with update-modules) - // alias net-pf-17 af_packet - // Then follow it by: # modprobe af_packet - if ((sock_fd = socket(PF_PACKET, SOCK_PACKET, htons(ETH_P_ALL))) < 0) - { - /* Error occured */ - fprintf(stderr, - "arcnet: Error opening socket: %s\n", - strerror(errno)); - fprintf(stderr, - "You might need to add the following to modules.conf\n" - "(or in /etc/modutils/alias on Debian with update-modules):\n" - "alias net-pf-17 af_packet\n" - "Also, add af_packet to /etc/modules.\n" - "Then follow it by:\n" - "# modprobe af_packet\n"); - exit(-1); - } - - if (ARCNET_Sock_FD >= 0) - { - /* Bind the socket to an interface name so we only get packets from it */ + /* check to see if we are being run as root */ + uid = getuid(); + if (uid != 0) { + fprintf(stderr, + "arcnet: Unable to open an af_packet socket. " + "Try running with root priveleges.\n"); + return sock_fd; + } + fprintf(stderr, "arcnet: opening \"%s\"\n", interface_name); + // note: on some systems you may have to add or enable in + // modules.conf (or in modutils/alias on Debian with update-modules) + // alias net-pf-17 af_packet + // Then follow it by: # modprobe af_packet + if ((sock_fd = socket(PF_PACKET, SOCK_PACKET, htons(ETH_P_ALL))) < 0) { + /* Error occured */ + fprintf(stderr, + "arcnet: Error opening socket: %s\n", strerror(errno)); + fprintf(stderr, + "You might need to add the following to modules.conf\n" + "(or in /etc/modutils/alias on Debian with update-modules):\n" + "alias net-pf-17 af_packet\n" + "Also, add af_packet to /etc/modules.\n" + "Then follow it by:\n" "# modprobe af_packet\n"); + exit(-1); + } + + if (ARCNET_Sock_FD >= 0) { + /* Bind the socket to an interface name so we only get packets from it */ + ARCNET_Socket_Address.sa_family = ARPHRD_ARCNET; + //ARCNET_Socket_Address.sa_family = PF_INET; + /* Clear the memory before copying */ + memset(ARCNET_Socket_Address.sa_data, '\0', + sizeof(ARCNET_Socket_Address.sa_data)); + /* Strcpy the interface name into the address */ + strncpy(ARCNET_Socket_Address.sa_data, interface_name, + sizeof(ARCNET_Socket_Address.sa_data) - 1); + fprintf(stderr, "arcnet: binding \"%s\"\n", + ARCNET_Socket_Address.sa_data); + if (bind(sock_fd, &ARCNET_Socket_Address, + sizeof(ARCNET_Socket_Address)) != 0) { + /* Bind problem, close socket and return */ + fprintf(stderr, + "arcnet: Unable to bind socket : %s\n", strerror(errno)); + fprintf(stderr, + "You might need to add the following to modules.conf\n" + "(or in /etc/modutils/alias on Debian with update-modules):\n" + "alias net-pf-17 af_packet\n" + "Also, add af_packet to /etc/modules.\n" + "Then follow it by:\n" "# modprobe af_packet\n"); + /* Close the socket */ + close(sock_fd); + exit(-1); + } + } + strncpy(ifr.ifr_name, interface_name, sizeof(ifr.ifr_name)); + rv = ioctl(sock_fd, SIOCGIFHWADDR, &ifr); + if (rv != -1) /* worked okay */ + ARCNET_MAC_Address = ifr.ifr_hwaddr.sa_data[0]; + // copy this info into the local copy since bind wiped it out ARCNET_Socket_Address.sa_family = ARPHRD_ARCNET; //ARCNET_Socket_Address.sa_family = PF_INET; /* Clear the memory before copying */ memset(ARCNET_Socket_Address.sa_data, '\0', - sizeof(ARCNET_Socket_Address.sa_data)); + sizeof(ARCNET_Socket_Address.sa_data)); /* Strcpy the interface name into the address */ - strncpy(ARCNET_Socket_Address.sa_data, interface_name, - sizeof(ARCNET_Socket_Address.sa_data)-1); - fprintf(stderr,"arcnet: binding \"%s\"\n",ARCNET_Socket_Address.sa_data); - if (bind(sock_fd, &ARCNET_Socket_Address, - sizeof(ARCNET_Socket_Address)) != 0) - { - /* Bind problem, close socket and return */ - fprintf(stderr, - "arcnet: Unable to bind socket : %s\n", - strerror(errno)); - fprintf(stderr, - "You might need to add the following to modules.conf\n" - "(or in /etc/modutils/alias on Debian with update-modules):\n" - "alias net-pf-17 af_packet\n" - "Also, add af_packet to /etc/modules.\n" - "Then follow it by:\n" - "# modprobe af_packet\n"); - /* Close the socket */ - close(sock_fd); - exit(-1); - } - } - strncpy(ifr.ifr_name, interface_name, sizeof(ifr.ifr_name)); - rv = ioctl(sock_fd, SIOCGIFHWADDR, &ifr); - if (rv != -1) /* worked okay */ - ARCNET_MAC_Address = ifr.ifr_hwaddr.sa_data[0]; - // copy this info into the local copy since bind wiped it out - ARCNET_Socket_Address.sa_family = ARPHRD_ARCNET; - //ARCNET_Socket_Address.sa_family = PF_INET; - /* Clear the memory before copying */ - memset(ARCNET_Socket_Address.sa_data, '\0', - sizeof(ARCNET_Socket_Address.sa_data)); - /* Strcpy the interface name into the address */ - strncpy(ARCNET_Socket_Address.sa_data, interface_name, - sizeof(ARCNET_Socket_Address.sa_data)-1); - fprintf(stderr,"arcnet: MAC=%02Xh iface=\"%s\"\n", - ARCNET_MAC_Address, - ARCNET_Socket_Address.sa_data); + strncpy(ARCNET_Socket_Address.sa_data, interface_name, + sizeof(ARCNET_Socket_Address.sa_data) - 1); + fprintf(stderr, "arcnet: MAC=%02Xh iface=\"%s\"\n", + ARCNET_MAC_Address, ARCNET_Socket_Address.sa_data); - atexit(arcnet_cleanup); + atexit(arcnet_cleanup); - return sock_fd; + return sock_fd; } bool arcnet_init(char *interface_name) { - ARCNET_Sock_FD = arcnet_bind(interface_name); + ARCNET_Sock_FD = arcnet_bind(interface_name); - return arcnet_valid(); + return arcnet_valid(); } /* function to send a packet out the socket */ /* returns number of bytes sent on success, negative on failure */ -int arcnet_send( - BACNET_ADDRESS *dest, // destination address - BACNET_ADDRESS *src, // source address - uint8_t *pdu, // any data to be sent - may be null - unsigned pdu_len) // number of bytes of data +int arcnet_send(BACNET_ADDRESS * dest, // destination address + BACNET_ADDRESS * src, // source address + uint8_t * pdu, // any data to be sent - may be null + unsigned pdu_len) // number of bytes of data { int bytes = 0; uint8_t mtu[512] = { 0 }; int mtu_len = 0; - struct archdr *pkt = (struct archdr *)mtu; + struct archdr *pkt = (struct archdr *) mtu; // don't waste time if the socket is not valid - if (ARCNET_Sock_FD < 0) - { + if (ARCNET_Sock_FD < 0) { fprintf(stderr, "arcnet: socket is invalid!\n"); return -1; } /* load destination MAC address */ if (dest->mac_len == 1) - pkt->hard.dest = dest->mac[0]; - else - { + pkt->hard.dest = dest->mac[0]; + else { fprintf(stderr, "arcnet: invalid destination MAC address!\n"); return -2; } if (src->mac_len == 1) - pkt->hard.source = src->mac[0]; - else - { + pkt->hard.source = src->mac[0]; + else { fprintf(stderr, "arcnet: invalid source MAC address!\n"); return -3; } - if ((ARC_HDR_SIZE + pdu_len) > 512) - { + if ((ARC_HDR_SIZE + pdu_len) > 512) { fprintf(stderr, "arcnet: PDU is too big to send!\n"); return -4; } /* Logical PDU portion */ - pkt->soft.raw[0] = 0xCD; /* SC for BACnet */ - pkt->soft.raw[1] = 0x82; /* DSAP for BACnet */ - pkt->soft.raw[2] = 0x82; /* SSAP for BACnet */ - pkt->soft.raw[3] = 0x03; /* Control byte in header */ + pkt->soft.raw[0] = 0xCD; /* SC for BACnet */ + pkt->soft.raw[1] = 0x82; /* DSAP for BACnet */ + pkt->soft.raw[2] = 0x82; /* SSAP for BACnet */ + pkt->soft.raw[3] = 0x03; /* Control byte in header */ memcpy(&pkt->soft.raw[4], pdu, pdu_len); /* packet length */ - mtu_len = ARC_HDR_SIZE + 4 /*SC,DSAP,SSAP,LLC*/ + pdu_len; + mtu_len = ARC_HDR_SIZE + 4 /*SC,DSAP,SSAP,LLC */ + pdu_len; /* Send the packet */ bytes = sendto(ARCNET_Sock_FD, &mtu, mtu_len, 0, - (struct sockaddr *) &ARCNET_Socket_Address, - sizeof(ARCNET_Socket_Address)); + (struct sockaddr *) &ARCNET_Socket_Address, + sizeof(ARCNET_Socket_Address)); /* did it get sent? */ if (bytes < 0) - fprintf(stderr,"arcnet: Error sending packet: %s\n", - strerror(errno)); - + fprintf(stderr, "arcnet: Error sending packet: %s\n", + strerror(errno)); + return bytes; } /* function to send a PDU out the socket */ /* returns number of bytes sent on success, negative on failure */ -int arcnet_send_pdu( - BACNET_ADDRESS *dest, // destination address - uint8_t *pdu, // any data to be sent - may be null - unsigned pdu_len) // number of bytes of data +int arcnet_send_pdu(BACNET_ADDRESS * dest, // destination address + uint8_t * pdu, // any data to be sent - may be null + unsigned pdu_len) // number of bytes of data { - BACNET_ADDRESS src = {0}; // source address - - src.mac[0] = ARCNET_MAC_Address; - src.mac_len = 1; - return arcnet_send(dest, // destination address - &src, // source address - pdu, // any data to be sent - may be null - pdu_len); // number of bytes of data + BACNET_ADDRESS src = { 0 }; // source address + + src.mac[0] = ARCNET_MAC_Address; + src.mac_len = 1; + return arcnet_send(dest, // destination address + &src, // source address + pdu, // any data to be sent - may be null + pdu_len); // number of bytes of data } // receives an framed packet // returns the number of octets in the PDU, or zero on failure -uint16_t arcnet_receive( - BACNET_ADDRESS *src, // source address - uint8_t *pdu, // PDU data - uint16_t max_pdu, // amount of space available in the PDU - unsigned timeout) // milliseconds to wait for a packet +uint16_t arcnet_receive(BACNET_ADDRESS * src, // source address + uint8_t * pdu, // PDU data + uint16_t max_pdu, // amount of space available in the PDU + unsigned timeout) // milliseconds to wait for a packet { int received_bytes; - uint8_t buf[512] = {0}; // data - uint16_t pdu_len = 0; // return value + uint8_t buf[512] = { 0 }; // data + uint16_t pdu_len = 0; // return value fd_set read_fds; int max; struct timeval select_timeout; - struct archdr *pkt = (struct archdr *)buf; + struct archdr *pkt = (struct archdr *) buf; /* Make sure the socket is open */ if (ARCNET_Sock_FD <= 0) @@ -289,14 +275,11 @@ uint16_t arcnet_receive( /* we could just use a non-blocking socket, but that consumes all the CPU time. We can use a timeout; it is only supported as a select. */ - if (timeout >= 1000) - { + if (timeout >= 1000) { select_timeout.tv_sec = timeout / 1000; - select_timeout.tv_usec = - 1000 * (timeout - select_timeout.tv_sec * 1000); - } - else - { + select_timeout.tv_usec = + 1000 * (timeout - select_timeout.tv_sec * 1000); + } else { select_timeout.tv_sec = 0; select_timeout.tv_usec = 1000 * timeout; } @@ -315,46 +298,44 @@ uint16_t arcnet_receive( // using O_NONBLOCK and no data // was immediately available for reading. if (errno != EAGAIN) - fprintf(stderr,"ethernet: Read error in receiving packet: %s\n", + fprintf(stderr, + "ethernet: Read error in receiving packet: %s\n", strerror(errno)); return 0; } if (received_bytes == 0) - return 0; + return 0; /* printf("arcnet: received %u bytes (offset=%02Xh %02Xh) " - "from %02Xh (proto==%02Xh)\n", - received_bytes, pkt->offset[0], pkt->offset[1], - pkt->hard.source, pkt->soft.raw[0]); - */ - + "from %02Xh (proto==%02Xh)\n", + received_bytes, pkt->offset[0], pkt->offset[1], + pkt->hard.source, pkt->soft.raw[0]); + */ + if (pkt->hard.source == ARCNET_MAC_Address) { - fprintf(stderr,"arcnet: self sent packet?\n"); + fprintf(stderr, "arcnet: self sent packet?\n"); return 0; } if (pkt->soft.raw[0] != 0xCD) { /* fprintf(stderr,"arcnet: Non-BACnet packet.\n"); */ return 0; } - if ((pkt->hard.dest != ARCNET_MAC_Address) && - (pkt->hard.dest != ARCNET_BROADCAST)) - { - fprintf(stderr,"arcnet: This packet is not for us.\n"); + if ((pkt->hard.dest != ARCNET_MAC_Address) && + (pkt->hard.dest != ARCNET_BROADCAST)) { + fprintf(stderr, "arcnet: This packet is not for us.\n"); return 0; } - if ((pkt->soft.raw[1] != 0x82) || /* DSAP */ - (pkt->soft.raw[2] != 0x82) || /* LSAP */ - (pkt->soft.raw[3] != 0x03)) /* LLC Control */ - { - fprintf(stderr,"arcnet: BACnet packet has invalid LLC.\n"); + if ((pkt->soft.raw[1] != 0x82) || /* DSAP */ + (pkt->soft.raw[2] != 0x82) || /* LSAP */ + (pkt->soft.raw[3] != 0x03)) { /* LLC Control */ + fprintf(stderr, "arcnet: BACnet packet has invalid LLC.\n"); return 0; } /* It must be addressed to us or be a Broadcast */ - if ((pkt->hard.dest != ARCNET_MAC_Address) && - (pkt->hard.dest != ARCNET_BROADCAST)) - { - fprintf(stderr,"arcnet: This packet is not for us.\n"); + if ((pkt->hard.dest != ARCNET_MAC_Address) && + (pkt->hard.dest != ARCNET_BROADCAST)) { + fprintf(stderr, "arcnet: This packet is not for us.\n"); return 0; } /* copy the source address */ @@ -365,47 +346,42 @@ uint16_t arcnet_receive( pdu_len -= 4 /* SC, DSAP, SSAP, LLC Control */ ; // copy the buffer into the PDU if (pdu_len < max_pdu) - memmove(&pdu[0],&pkt->soft.raw[4],pdu_len); + memmove(&pdu[0], &pkt->soft.raw[4], pdu_len); // silently ignore packets that are too large else - pdu_len = 0; + pdu_len = 0; return pdu_len; } -void arcnet_get_my_address(BACNET_ADDRESS *my_address) +void arcnet_get_my_address(BACNET_ADDRESS * my_address) { - int i = 0; - - my_address->mac_len = 1; - my_address->mac[0] = ARCNET_MAC_Address; - my_address->net = 0; // local only, no routing - my_address->len = 0; - for (i = 0; i < MAX_MAC_LEN; i++) - { - my_address->adr[i] = 0; - } + int i = 0; - return; -} - -void arcnet_get_broadcast_address( - BACNET_ADDRESS *dest) // destination address -{ - int i = 0; // counter - - if (dest) - { - dest->mac[0] = ARCNET_BROADCAST; - dest->mac_len = 1; - dest->net = BACNET_BROADCAST_NETWORK; - dest->len = 0; // len=0 denotes broadcast address - for (i = 0; i < MAX_MAC_LEN; i++) - { - dest->adr[i] = 0; + my_address->mac_len = 1; + my_address->mac[0] = ARCNET_MAC_Address; + my_address->net = 0; // local only, no routing + my_address->len = 0; + for (i = 0; i < MAX_MAC_LEN; i++) { + my_address->adr[i] = 0; } - } - return; + return; } +void arcnet_get_broadcast_address(BACNET_ADDRESS * dest) // destination address +{ + int i = 0; // counter + + if (dest) { + dest->mac[0] = ARCNET_BROADCAST; + dest->mac_len = 1; + dest->net = BACNET_BROADCAST_NETWORK; + dest->len = 0; // len=0 denotes broadcast address + for (i = 0; i < MAX_MAC_LEN; i++) { + dest->adr[i] = 0; + } + } + + return; +} diff --git a/bacnet-stack/ports/linux/bip-init.c b/bacnet-stack/ports/linux/bip-init.c index 70dee18d..286c346c 100644 --- a/bacnet-stack/ports/linux/bip-init.c +++ b/bacnet-stack/ports/linux/bip-init.c @@ -39,7 +39,8 @@ #include "net.h" -static int get_local_ifr_ioctl(char *ifname, struct ifreq *ifr, int request) +static int get_local_ifr_ioctl(char *ifname, struct ifreq *ifr, + int request) { int fd; int rv; // return value @@ -54,16 +55,14 @@ static int get_local_ifr_ioctl(char *ifname, struct ifreq *ifr, int request) return rv; } -static int get_local_address_ioctl( - char *ifname, - struct in_addr *addr, - int request) +static int get_local_address_ioctl(char *ifname, + struct in_addr *addr, int request) { struct ifreq ifr = { {{0}} }; struct sockaddr_in *tcpip_address; int rv; // return value - rv = get_local_ifr_ioctl(ifname,&ifr,request); + rv = get_local_ifr_ioctl(ifname, &ifr, request); if (rv >= 0) { tcpip_address = (struct sockaddr_in *) &ifr.ifr_addr; memcpy(addr, &tcpip_address->sin_addr, sizeof(struct in_addr)); @@ -80,20 +79,21 @@ void bip_set_interface(char *ifname) /* setup local address */ get_local_address_ioctl(ifname, &local_address, SIOCGIFADDR); bip_set_addr(local_address.s_addr); - #ifdef BIP_DEBUG - fprintf(stderr,"IP Address: %s\n",inet_ntoa(local_address)); - #endif +#ifdef BIP_DEBUG + fprintf(stderr, "IP Address: %s\n", inet_ntoa(local_address)); +#endif /* setup local broadcast address */ get_local_address_ioctl(ifname, &broadcast_address, SIOCGIFBRDADDR); bip_set_broadcast_addr(broadcast_address.s_addr); - #ifdef BIP_DEBUG - fprintf(stderr,"Broadcast Address: %s\n",inet_ntoa(broadcast_address)); - #endif +#ifdef BIP_DEBUG + fprintf(stderr, "Broadcast Address: %s\n", + inet_ntoa(broadcast_address)); +#endif } bool bip_init(void) { - int status = 0; // return from socket lib calls + int status = 0; // return from socket lib calls struct sockaddr_in sin; int sockopt = 0; int sock_fd = -1; @@ -108,8 +108,7 @@ bool bip_init(void) sockopt = 1; status = setsockopt(sock_fd, SOL_SOCKET, SO_REUSEADDR, &sockopt, sizeof(sockopt)); - if (status < 0) - { + if (status < 0) { close(sock_fd); bip_set_socket(-1); return status; @@ -117,22 +116,19 @@ bool bip_init(void) // allow us to send a broadcast status = setsockopt(sock_fd, SOL_SOCKET, SO_BROADCAST, &sockopt, sizeof(sockopt)); - if (status < 0) - { + if (status < 0) { close(sock_fd); bip_set_socket(-1); return status; } - // bind the socket to the local port number and IP address sin.sin_family = AF_INET; sin.sin_addr.s_addr = htonl(INADDR_ANY); sin.sin_port = htons(bip_get_port()); memset(&(sin.sin_zero), '\0', sizeof(sin.sin_zero)); status = bind(sock_fd, - (const struct sockaddr*)&sin, sizeof(struct sockaddr)); - if (status < 0) - { + (const struct sockaddr *) &sin, sizeof(struct sockaddr)); + if (status < 0) { close(sock_fd); bip_set_socket(-1); return false; diff --git a/bacnet-stack/ports/linux/ethernet.c b/bacnet-stack/ports/linux/ethernet.c index 1ad88b47..e2bb0158 100644 --- a/bacnet-stack/ports/linux/ethernet.c +++ b/bacnet-stack/ports/linux/ethernet.c @@ -45,24 +45,25 @@ uint8_t Ethernet_Broadcast[MAX_MAC_LEN] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }; // commonly used empty address for ethernet quick compare uint8_t Ethernet_Empty_MAC[MAX_MAC_LEN] = { 0, 0, 0, 0, 0, 0 }; + // my local device data - MAC address uint8_t Ethernet_MAC_Address[MAX_MAC_LEN] = { 0 }; -static int eth802_sockfd = -1; /* 802.2 file handle */ -static struct sockaddr eth_addr = { 0 }; // used for binding 802.2 +static int eth802_sockfd = -1; /* 802.2 file handle */ +static struct sockaddr eth_addr = { 0 }; // used for binding 802.2 bool ethernet_valid(void) { - return (eth802_sockfd >= 0); + return (eth802_sockfd >= 0); } void ethernet_cleanup(void) { - if (ethernet_valid()) - close(eth802_sockfd); - eth802_sockfd = -1; + if (ethernet_valid()) + close(eth802_sockfd); + eth802_sockfd = -1; - return; + return; } /*---------------------------------------------------------------------- @@ -76,23 +77,23 @@ void ethernet_cleanup(void) ----------------------------------------------------------------------*/ int setNonblocking(int fd) { - int flags; + int flags; - if (-1 == (flags = fcntl(fd, F_GETFL, 0))) - flags = 0; - return fcntl(fd, F_SETFL, flags | O_NONBLOCK); -} + if (-1 == (flags = fcntl(fd, F_GETFL, 0))) + flags = 0; + return fcntl(fd, F_SETFL, flags | O_NONBLOCK); +} /* opens an 802.2 socket to receive and send packets */ static int ethernet_bind(struct sockaddr *eth_addr, char *interface_name) { - int sock_fd = -1; // return value + int sock_fd = -1; // return value int uid = 0; - fprintf(stderr,"ethernet: opening \"%s\"\n",interface_name); + fprintf(stderr, "ethernet: opening \"%s\"\n", interface_name); /* check to see if we are being run as root */ uid = getuid(); - if (uid != 0) { + if (uid != 0) { fprintf(stderr, "ethernet: Unable to open an 802.2 socket. " "Try running with root priveleges.\n"); @@ -102,21 +103,18 @@ static int ethernet_bind(struct sockaddr *eth_addr, char *interface_name) // modules.conf (or in modutils/alias on Debian with update-modules) // alias net-pf-17 af_packet // Then follow it by: # modprobe af_packet - + /* Attempt to open the socket for 802.2 ethernet frames */ - if ((sock_fd = socket(PF_INET, SOCK_PACKET, htons(ETH_P_802_2))) < 0) - { + if ((sock_fd = socket(PF_INET, SOCK_PACKET, htons(ETH_P_802_2))) < 0) { /* Error occured */ fprintf(stderr, - "ethernet: Error opening socket: %s\n", - strerror(errno)); + "ethernet: Error opening socket: %s\n", strerror(errno)); fprintf(stderr, "You might need to add the following to modules.conf\n" "(or in /etc/modutils/alias on Debian with update-modules):\n" "alias net-pf-17 af_packet\n" "Also, add af_packet to /etc/modules.\n" - "Then follow it by:\n" - "# modprobe af_packet\n"); + "Then follow it by:\n" "# modprobe af_packet\n"); exit(-1); } /* Bind the socket to an address */ @@ -124,11 +122,11 @@ static int ethernet_bind(struct sockaddr *eth_addr, char *interface_name) /* Clear the memory before copying */ memset(eth_addr->sa_data, '\0', sizeof(eth_addr->sa_data)); /* Strcpy the interface name into the address */ - strncpy(eth_addr->sa_data, interface_name, sizeof(eth_addr->sa_data)-1); - fprintf(stderr,"ethernet: binding \"%s\"\n",eth_addr->sa_data); + strncpy(eth_addr->sa_data, interface_name, + sizeof(eth_addr->sa_data) - 1); + fprintf(stderr, "ethernet: binding \"%s\"\n", eth_addr->sa_data); /* Attempt to bind the socket to the interface */ - if (bind(sock_fd, eth_addr, sizeof(struct sockaddr)) != 0) - { + if (bind(sock_fd, eth_addr, sizeof(struct sockaddr)) != 0) { /* Bind problem, close socket and return */ fprintf(stderr, "ethernet: Unable to bind 802.2 socket : %s\n", @@ -138,8 +136,7 @@ static int ethernet_bind(struct sockaddr *eth_addr, char *interface_name) "(or in /etc/modutils/alias on Debian with update-modules):\n" "alias net-pf-17 af_packet\n" "Also, add af_packet to /etc/modules.\n" - "Then follow it by:\n" - "# modprobe af_packet\n"); + "Then follow it by:\n" "# modprobe af_packet\n"); /* Close the socket */ close(sock_fd); exit(-1); @@ -155,7 +152,7 @@ static int get_local_hwaddr(const char *ifname, unsigned char *mac) { struct ifreq ifr; int fd; - int rv; // return value - error value from df or ioctl call + int rv; // return value - error value from df or ioctl call /* determine the local MAC address */ strcpy(ifr.ifr_name, ifname); @@ -174,19 +171,17 @@ static int get_local_hwaddr(const char *ifname, unsigned char *mac) bool ethernet_init(char *interface_name) { get_local_hwaddr(interface_name, Ethernet_MAC_Address); - eth802_sockfd = - ethernet_bind(ð_addr, interface_name); + eth802_sockfd = ethernet_bind(ð_addr, interface_name); - return ethernet_valid(); + return ethernet_valid(); } /* function to send a packet out the 802.2 socket */ /* returns bytes sent success, negative on failure */ -int ethernet_send( - BACNET_ADDRESS *dest, // destination address - BACNET_ADDRESS *src, // source address - uint8_t *pdu, // any data to be sent - may be null - unsigned pdu_len) // number of bytes of data +int ethernet_send(BACNET_ADDRESS * dest, // destination address + BACNET_ADDRESS * src, // source address + uint8_t * pdu, // any data to be sent - may be null + unsigned pdu_len) // number of bytes of data { int bytes = 0; uint8_t mtu[MAX_MPDU] = { 0 }; @@ -194,101 +189,88 @@ int ethernet_send( int i = 0; // don't waste time if the socket is not valid - if (eth802_sockfd < 0) - { + if (eth802_sockfd < 0) { fprintf(stderr, "ethernet: 802.2 socket is invalid!\n"); return -1; } /* load destination ethernet MAC address */ - if (dest->mac_len == 6) - { - for (i = 0; i < 6; i++) - { - mtu[mtu_len] = dest->mac[i]; - mtu_len++; - } - } - else - { + if (dest->mac_len == 6) { + for (i = 0; i < 6; i++) { + mtu[mtu_len] = dest->mac[i]; + mtu_len++; + } + } else { fprintf(stderr, "ethernet: invalid destination MAC address!\n"); return -2; } /* load source ethernet MAC address */ - if (src->mac_len == 6) - { - for (i = 0; i < 6; i++) - { - mtu[mtu_len] = src->mac[i]; - mtu_len++; - } - } - else - { + if (src->mac_len == 6) { + for (i = 0; i < 6; i++) { + mtu[mtu_len] = src->mac[i]; + mtu_len++; + } + } else { fprintf(stderr, "ethernet: invalid source MAC address!\n"); return -3; } - if ((14 + 3 + pdu_len) > MAX_MPDU) - { + if ((14 + 3 + pdu_len) > MAX_MPDU) { fprintf(stderr, "ethernet: PDU is too big to send!\n"); return -4; } /* packet length */ - mtu_len += encode_unsigned16(&mtu[12], - 3 /*DSAP,SSAP,LLC*/ + pdu_len); + mtu_len += encode_unsigned16(&mtu[12], + 3 /*DSAP,SSAP,LLC */ + pdu_len); // Logical PDU portion - mtu[mtu_len++] = 0x82; /* DSAP for BACnet */ - mtu[mtu_len++] = 0x82; /* SSAP for BACnet */ - mtu[mtu_len++] = 0x03; /* Control byte in header */ + mtu[mtu_len++] = 0x82; /* DSAP for BACnet */ + mtu[mtu_len++] = 0x82; /* SSAP for BACnet */ + mtu[mtu_len++] = 0x03; /* Control byte in header */ memcpy(&mtu[mtu_len], pdu, pdu_len); mtu_len += pdu_len; - + /* Send the packet */ bytes = sendto(eth802_sockfd, &mtu, mtu_len, 0, (struct sockaddr *) ð_addr, sizeof(struct sockaddr)); /* did it get sent? */ if (bytes < 0) - fprintf(stderr,"ethernet: Error sending packet: %s\n", - strerror(errno)); - + fprintf(stderr, "ethernet: Error sending packet: %s\n", + strerror(errno)); + return bytes; } /* function to send a packet out the 802.2 socket */ /* returns number of bytes sent on success, negative on failure */ -int ethernet_send_pdu( - BACNET_ADDRESS *dest, // destination address - uint8_t *pdu, // any data to be sent - may be null - unsigned pdu_len) // number of bytes of data +int ethernet_send_pdu(BACNET_ADDRESS * dest, // destination address + uint8_t * pdu, // any data to be sent - may be null + unsigned pdu_len) // number of bytes of data { - int i = 0; // counter - BACNET_ADDRESS src = {0}; // source address - - for (i = 0; i < 6; i++) - { - src.mac[i] = Ethernet_MAC_Address[i]; - src.mac_len++; - } - /* function to send a packet out the 802.2 socket */ - /* returns 1 on success, 0 on failure */ - return ethernet_send(dest, // destination address - &src, // source address - pdu, // any data to be sent - may be null - pdu_len); // number of bytes of data + int i = 0; // counter + BACNET_ADDRESS src = { 0 }; // source address + + for (i = 0; i < 6; i++) { + src.mac[i] = Ethernet_MAC_Address[i]; + src.mac_len++; + } + /* function to send a packet out the 802.2 socket */ + /* returns 1 on success, 0 on failure */ + return ethernet_send(dest, // destination address + &src, // source address + pdu, // any data to be sent - may be null + pdu_len); // number of bytes of data } // receives an 802.2 framed packet // returns the number of octets in the PDU, or zero on failure -uint16_t ethernet_receive( - BACNET_ADDRESS *src, // source address - uint8_t *pdu, // PDU data - uint16_t max_pdu, // amount of space available in the PDU - unsigned timeout) // number of milliseconds to wait for a packet +uint16_t ethernet_receive(BACNET_ADDRESS * src, // source address + uint8_t * pdu, // PDU data + uint16_t max_pdu, // amount of space available in the PDU + unsigned timeout) // number of milliseconds to wait for a packet { int received_bytes; - uint8_t buf[MAX_MPDU] = {0}; // data - uint16_t pdu_len = 0; // return value + uint8_t buf[MAX_MPDU] = { 0 }; // data + uint16_t pdu_len = 0; // return value fd_set read_fds; int max; struct timeval select_timeout; @@ -300,14 +282,11 @@ uint16_t ethernet_receive( /* we could just use a non-blocking socket, but that consumes all the CPU time. We can use a timeout; it is only supported as a select. */ - if (timeout >= 1000) - { + if (timeout >= 1000) { select_timeout.tv_sec = timeout / 1000; - select_timeout.tv_usec = - 1000 * (timeout - select_timeout.tv_sec * 1000); - } - else - { + select_timeout.tv_usec = + 1000 * (timeout - select_timeout.tv_sec * 1000); + } else { select_timeout.tv_sec = 0; select_timeout.tv_usec = 1000 * timeout; } @@ -326,14 +305,15 @@ uint16_t ethernet_receive( // using O_NONBLOCK and no data // was immediately available for reading. if (errno != EAGAIN) - fprintf(stderr,"ethernet: Read error in receiving packet: %s\n", + fprintf(stderr, + "ethernet: Read error in receiving packet: %s\n", strerror(errno)); return 0; } if (received_bytes == 0) - return 0; - + return 0; + /* the signature of an 802.2 BACnet packet */ if ((buf[14] != 0x82) && (buf[15] != 0x82)) { //fprintf(stderr,"ethernet: Non-BACnet packet\n"); @@ -345,109 +325,95 @@ uint16_t ethernet_receive( // check destination address for when // the Ethernet card is in promiscious mode - if ((memcmp(&buf[0], Ethernet_MAC_Address,6) != 0) - && (memcmp(&buf[0], Ethernet_Broadcast, 6) != 0)) - { + if ((memcmp(&buf[0], Ethernet_MAC_Address, 6) != 0) + && (memcmp(&buf[0], Ethernet_Broadcast, 6) != 0)) { //fprintf(stderr, "ethernet: This packet isn't for us\n"); return 0; } - (void)decode_unsigned16(&buf[12],&pdu_len); + (void) decode_unsigned16(&buf[12], &pdu_len); pdu_len -= 3 /* DSAP, SSAP, LLC Control */ ; // copy the buffer into the PDU if (pdu_len < max_pdu) - memmove(&pdu[0],&buf[17],pdu_len); + memmove(&pdu[0], &buf[17], pdu_len); // ignore packets that are too large else - pdu_len = 0; - + pdu_len = 0; + return pdu_len; } -void ethernet_set_my_address(BACNET_ADDRESS *my_address) +void ethernet_set_my_address(BACNET_ADDRESS * my_address) { - int i = 0; - - for (i = 0; i < 6; i++) - { - Ethernet_MAC_Address[i] = my_address->mac[i]; - } + int i = 0; - return; + for (i = 0; i < 6; i++) { + Ethernet_MAC_Address[i] = my_address->mac[i]; + } + + return; } -void ethernet_get_my_address(BACNET_ADDRESS *my_address) +void ethernet_get_my_address(BACNET_ADDRESS * my_address) { - int i = 0; - - my_address->mac_len = 0; - for (i = 0; i < 6; i++) - { - my_address->mac[i] = Ethernet_MAC_Address[i]; - my_address->mac_len++; - } - my_address->net = 0; // local only, no routing - my_address->len = 0; - for (i = 0; i < MAX_MAC_LEN; i++) - { - my_address->adr[i] = 0; - } + int i = 0; - return; + my_address->mac_len = 0; + for (i = 0; i < 6; i++) { + my_address->mac[i] = Ethernet_MAC_Address[i]; + my_address->mac_len++; + } + my_address->net = 0; // local only, no routing + my_address->len = 0; + for (i = 0; i < MAX_MAC_LEN; i++) { + my_address->adr[i] = 0; + } + + return; } -void ethernet_get_broadcast_address( - BACNET_ADDRESS *dest) // destination address +void ethernet_get_broadcast_address(BACNET_ADDRESS * dest) // destination address { - int i = 0; // counter - - if (dest) - { - for (i = 0; i < 6; i++) - { - dest->mac[i] = Ethernet_Broadcast[i]; - } - dest->mac_len = 6; - dest->net = BACNET_BROADCAST_NETWORK; - dest->len = 0; // denotes broadcast address - for (i = 0; i < MAX_MAC_LEN; i++) - { - dest->adr[i] = 0; - } - } + int i = 0; // counter - return; + if (dest) { + for (i = 0; i < 6; i++) { + dest->mac[i] = Ethernet_Broadcast[i]; + } + dest->mac_len = 6; + dest->net = BACNET_BROADCAST_NETWORK; + dest->len = 0; // denotes broadcast address + for (i = 0; i < MAX_MAC_LEN; i++) { + dest->adr[i] = 0; + } + } + + return; } -void ethernet_debug_address( - const char *info, - BACNET_ADDRESS *dest) +void ethernet_debug_address(const char *info, BACNET_ADDRESS * dest) { - int i = 0; // counter + int i = 0; // counter - if (info) - fprintf(stderr,"%s",info); - if (dest) - { - fprintf(stderr,"Address:\n"); - fprintf(stderr," MAC Length=%d\n",dest->mac_len); - fprintf(stderr," MAC Address="); - for (i = 0; i < MAX_MAC_LEN; i++) - { - fprintf(stderr,"%02X ",(unsigned)dest->mac[i]); + if (info) + fprintf(stderr, "%s", info); + if (dest) { + fprintf(stderr, "Address:\n"); + fprintf(stderr, " MAC Length=%d\n", dest->mac_len); + fprintf(stderr, " MAC Address="); + for (i = 0; i < MAX_MAC_LEN; i++) { + fprintf(stderr, "%02X ", (unsigned) dest->mac[i]); + } + fprintf(stderr, "\n"); + fprintf(stderr, " Net=%hu\n", dest->net); + fprintf(stderr, " Len=%d\n", dest->len); + fprintf(stderr, " Adr="); + for (i = 0; i < MAX_MAC_LEN; i++) { + fprintf(stderr, "%02X ", (unsigned) dest->adr[i]); + } + fprintf(stderr, "\n"); } - fprintf(stderr,"\n"); - fprintf(stderr," Net=%hu\n",dest->net); - fprintf(stderr," Len=%d\n",dest->len); - fprintf(stderr," Adr="); - for (i = 0; i < MAX_MAC_LEN; i++) - { - fprintf(stderr,"%02X ",(unsigned)dest->adr[i]); - } - fprintf(stderr,"\n"); - } - return; + return; } - diff --git a/bacnet-stack/ports/linux/main.c b/bacnet-stack/ports/linux/main.c index dfb206f7..d1ad5963 100644 --- a/bacnet-stack/ports/linux/main.c +++ b/bacnet-stack/ports/linux/main.c @@ -48,293 +48,251 @@ bool Who_Is_Request = true; // buffers used for receiving -static uint8_t Rx_Buf[MAX_MPDU] = {0}; +static uint8_t Rx_Buf[MAX_MPDU] = { 0 }; -static void LocalIAmHandler( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src) +static void LocalIAmHandler(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src) { - int len = 0; - uint32_t device_id = 0; - unsigned max_apdu = 0; - int segmentation = 0; - uint16_t vendor_id = 0; + int len = 0; + uint32_t device_id = 0; + unsigned max_apdu = 0; + int segmentation = 0; + uint16_t vendor_id = 0; - (void)src; - (void)service_len; - len = iam_decode_service_request( - service_request, - &device_id, - &max_apdu, - &segmentation, - &vendor_id); - fprintf(stderr,"Received I-Am Request"); - if (len != -1) - { - fprintf(stderr," from %u!\n",device_id); - address_add(device_id, - max_apdu, - src); - } - else - fprintf(stderr,"!\n"); + (void) src; + (void) service_len; + len = iam_decode_service_request(service_request, + &device_id, &max_apdu, &segmentation, &vendor_id); + fprintf(stderr, "Received I-Am Request"); + if (len != -1) { + fprintf(stderr, " from %u!\n", device_id); + address_add(device_id, max_apdu, src); + } else + fprintf(stderr, "!\n"); - return; + return; } static void Read_Properties(void) { - uint32_t device_id = 0; - bool status = false; - unsigned max_apdu = 0; - BACNET_ADDRESS src; - bool next_device = false; - static unsigned index = 0; - static unsigned property = 0; - /* list of required (and some optional and proprietary) - properties in the Device Object. Note that this demo - tests for error messages so that the device doesn't have - to have all the properties listed here. */ - const int object_props[] = - { - PROP_OBJECT_IDENTIFIER, - PROP_OBJECT_NAME, - PROP_OBJECT_TYPE, - PROP_SYSTEM_STATUS, - PROP_VENDOR_NAME, - PROP_VENDOR_IDENTIFIER, - PROP_MODEL_NAME, - PROP_FIRMWARE_REVISION, - PROP_APPLICATION_SOFTWARE_VERSION, - PROP_PROTOCOL_VERSION, - PROP_PROTOCOL_CONFORMANCE_CLASS, - PROP_PROTOCOL_SERVICES_SUPPORTED, - PROP_PROTOCOL_OBJECT_TYPES_SUPPORTED, - PROP_MAX_APDU_LENGTH_ACCEPTED, - PROP_SEGMENTATION_SUPPORTED, - PROP_LOCAL_TIME, - PROP_LOCAL_DATE, - PROP_UTC_OFFSET, - PROP_DAYLIGHT_SAVINGS_STATUS, - PROP_APDU_SEGMENT_TIMEOUT, - PROP_APDU_TIMEOUT, - PROP_NUMBER_OF_APDU_RETRIES, - PROP_TIME_SYNCHRONIZATION_RECIPIENTS, - PROP_MAX_MASTER, - PROP_MAX_INFO_FRAMES, - PROP_DEVICE_ADDRESS_BINDING, - /* note: PROP_OBJECT_LIST is missing because - the result can be very large. Read index 0 - which gives us the number of objects in the list, - and then we can read index 1, 2.. n one by one, - rather than trying to read the entire object - list in one message. */ - /* some proprietary properties */ - 514,515, - /* end of list */ - -1 - }; + uint32_t device_id = 0; + bool status = false; + unsigned max_apdu = 0; + BACNET_ADDRESS src; + bool next_device = false; + static unsigned index = 0; + static unsigned property = 0; + /* list of required (and some optional and proprietary) + properties in the Device Object. Note that this demo + tests for error messages so that the device doesn't have + to have all the properties listed here. */ + const int object_props[] = { + PROP_OBJECT_IDENTIFIER, + PROP_OBJECT_NAME, + PROP_OBJECT_TYPE, + PROP_SYSTEM_STATUS, + PROP_VENDOR_NAME, + PROP_VENDOR_IDENTIFIER, + PROP_MODEL_NAME, + PROP_FIRMWARE_REVISION, + PROP_APPLICATION_SOFTWARE_VERSION, + PROP_PROTOCOL_VERSION, + PROP_PROTOCOL_CONFORMANCE_CLASS, + PROP_PROTOCOL_SERVICES_SUPPORTED, + PROP_PROTOCOL_OBJECT_TYPES_SUPPORTED, + PROP_MAX_APDU_LENGTH_ACCEPTED, + PROP_SEGMENTATION_SUPPORTED, + PROP_LOCAL_TIME, + PROP_LOCAL_DATE, + PROP_UTC_OFFSET, + PROP_DAYLIGHT_SAVINGS_STATUS, + PROP_APDU_SEGMENT_TIMEOUT, + PROP_APDU_TIMEOUT, + PROP_NUMBER_OF_APDU_RETRIES, + PROP_TIME_SYNCHRONIZATION_RECIPIENTS, + PROP_MAX_MASTER, + PROP_MAX_INFO_FRAMES, + PROP_DEVICE_ADDRESS_BINDING, + /* note: PROP_OBJECT_LIST is missing because + the result can be very large. Read index 0 + which gives us the number of objects in the list, + and then we can read index 1, 2.. n one by one, + rather than trying to read the entire object + list in one message. */ + /* some proprietary properties */ + 514, 515, + /* end of list */ + -1 + }; - if (address_count()) - { - if (address_get_by_index(index, &device_id, &max_apdu, &src)) - { - if (object_props[property] < 0) - next_device = true; - else - { - /* note: if we wanted to do this synchronously, we would get the - invoke ID from the sending of the request, and wait until we - got the reply with matching invoke ID or the TSM of the - invoke ID expired. This demo is doing things asynchronously. */ - status = Send_Read_Property_Request( - device_id, // destination device - OBJECT_DEVICE, - device_id, - object_props[property], - BACNET_ARRAY_ALL); - if (status) - property++; - } + if (address_count()) { + if (address_get_by_index(index, &device_id, &max_apdu, &src)) { + if (object_props[property] < 0) + next_device = true; + else { + /* note: if we wanted to do this synchronously, we would get the + invoke ID from the sending of the request, and wait until we + got the reply with matching invoke ID or the TSM of the + invoke ID expired. This demo is doing things asynchronously. */ + status = Send_Read_Property_Request(device_id, // destination device + OBJECT_DEVICE, + device_id, object_props[property], BACNET_ARRAY_ALL); + if (status) + property++; + } + } else + next_device = true; + if (next_device) { + next_device = false; + index++; + if (index >= MAX_ADDRESS_CACHE) + index = 0; + property = 0; + } } - else - next_device = true; - if (next_device) - { - next_device = false; - index++; - if (index >= MAX_ADDRESS_CACHE) - index = 0; - property = 0; - } - } - return; + return; } - + static void Init_Service_Handlers(void) { - // we need to handle who-is to support dynamic device binding - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_WHO_IS, - handler_who_is); - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_I_AM, - LocalIAmHandler); + // we need to handle who-is to support dynamic device binding + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_WHO_IS, + handler_who_is); + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_I_AM, + LocalIAmHandler); - // set the handler for all the services we don't implement - // It is required to send the proper reject message... - apdu_set_unrecognized_service_handler_handler( - handler_unrecognized_service); - // Set the handlers for any confirmed services that we support. - // We must implement read property - it's required! - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property); - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_WRITE_PROPERTY, - handler_write_property); - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_ATOMIC_READ_FILE, - handler_atomic_read_file); - // handle the data coming back from confirmed requests - apdu_set_confirmed_ack_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property_ack); - apdu_set_confirmed_ack_handler( - SERVICE_CONFIRMED_ATOMIC_READ_FILE, - handler_atomic_read_file_ack); + // set the handler for all the services we don't implement + // It is required to send the proper reject message... + apdu_set_unrecognized_service_handler_handler + (handler_unrecognized_service); + // Set the handlers for any confirmed services that we support. + // We must implement read property - it's required! + apdu_set_confirmed_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property); + apdu_set_confirmed_handler(SERVICE_CONFIRMED_WRITE_PROPERTY, + handler_write_property); + apdu_set_confirmed_handler(SERVICE_CONFIRMED_ATOMIC_READ_FILE, + handler_atomic_read_file); + // handle the data coming back from confirmed requests + apdu_set_confirmed_ack_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property_ack); + apdu_set_confirmed_ack_handler(SERVICE_CONFIRMED_ATOMIC_READ_FILE, + handler_atomic_read_file_ack); } static void print_address_cache(void) { - unsigned i,j; - BACNET_ADDRESS address; - uint32_t device_id = 0; - unsigned max_apdu = 0; - - fprintf(stderr,"Device\tMAC\tMaxAPDU\tNet\n"); - for (i = 0; i < MAX_ADDRESS_CACHE; i++) - { - if (address_get_by_index(i,&device_id, &max_apdu, &address)) - { - fprintf(stderr,"%u\t",device_id); - for (j = 0; j < address.mac_len; j++) - { - fprintf(stderr,"%02X",address.mac[j]); - } - fprintf(stderr,"\t"); - fprintf(stderr,"%hu\t",max_apdu); - fprintf(stderr,"%hu\n",address.net); + unsigned i, j; + BACNET_ADDRESS address; + uint32_t device_id = 0; + unsigned max_apdu = 0; + + fprintf(stderr, "Device\tMAC\tMaxAPDU\tNet\n"); + for (i = 0; i < MAX_ADDRESS_CACHE; i++) { + if (address_get_by_index(i, &device_id, &max_apdu, &address)) { + fprintf(stderr, "%u\t", device_id); + for (j = 0; j < address.mac_len; j++) { + fprintf(stderr, "%02X", address.mac[j]); + } + fprintf(stderr, "\t"); + fprintf(stderr, "%hu\t", max_apdu); + fprintf(stderr, "%hu\n", address.net); + } } - } } static void print_tsm_stats(void) { - int idle = 0; - int total = 0; + int idle = 0; + int total = 0; - idle = tsm_transaction_idle_count(); - total = MAX_TSM_TRANSACTIONS; - fprintf(stderr,"TSM: %d idle of %d transactions\n",idle,total); + idle = tsm_transaction_idle_count(); + total = MAX_TSM_TRANSACTIONS; + fprintf(stderr, "TSM: %d idle of %d transactions\n", idle, total); } static void sig_handler(int signo) { - datalink_cleanup(); - print_address_cache(); - print_tsm_stats(); - - exit(0); + datalink_cleanup(); + print_address_cache(); + print_tsm_stats(); + + exit(0); } int main(int argc, char *argv[]) { - BACNET_ADDRESS src = {0}; // address where message came from - uint16_t pdu_len = 0; - unsigned timeout = 100; // milliseconds - unsigned count = 0; // milliseconds - time_t start_time; - time_t new_time = 0; - - start_time = time(NULL); /* get current time */ - // Linux specials - signal(SIGINT, sig_handler); - signal(SIGHUP, sig_handler); - signal(SIGTERM, sig_handler); - // setup this BACnet Server device - Device_Set_Object_Instance_Number(111); - Init_Service_Handlers(); - #ifdef BACDL_ETHERNET - // init the physical layer - if (!ethernet_init("eth0")) - return 1; - #endif - #ifdef BACDL_BIP - bip_set_interface("eth0"); - bip_set_port(0xBAC0); - if (!bip_init()) - return 1; - #endif - #ifdef BACDL_ARCNET - if (!arcnet_init("arc0")) - return 1; - #endif + BACNET_ADDRESS src = { 0 }; // address where message came from + uint16_t pdu_len = 0; + unsigned timeout = 100; // milliseconds + unsigned count = 0; // milliseconds + time_t start_time; + time_t new_time = 0; - // loop forever - for (;;) - { - // input - new_time = time(NULL); - // returns 0 bytes on timeout - pdu_len = datalink_receive( - &src, - &Rx_Buf[0], - MAX_MPDU, - timeout); + start_time = time(NULL); /* get current time */ + // Linux specials + signal(SIGINT, sig_handler); + signal(SIGHUP, sig_handler); + signal(SIGTERM, sig_handler); + // setup this BACnet Server device + Device_Set_Object_Instance_Number(111); + Init_Service_Handlers(); +#ifdef BACDL_ETHERNET + // init the physical layer + if (!ethernet_init("eth0")) + return 1; +#endif +#ifdef BACDL_BIP + bip_set_interface("eth0"); + bip_set_port(0xBAC0); + if (!bip_init()) + return 1; +#endif +#ifdef BACDL_ARCNET + if (!arcnet_init("arc0")) + return 1; +#endif - // process - if (pdu_len) - { - npdu_handler( - &src, - &Rx_Buf[0], - pdu_len); - } - if (new_time > start_time) - { - tsm_timer_milliseconds(new_time - start_time * 1000); - start_time = new_time; - } - if (I_Am_Request) - { - I_Am_Request = false; - iam_send(&Handler_Transmit_Buffer[0]); - } else if (Who_Is_Request) - { - Who_Is_Request = false; - Send_WhoIs(-1,-1); - } - // output - // some round robin task switching - count++; - switch (count) - { - case 1: - // used for testing, but kind of noisy on the network - //Read_Properties(); - break; - case 2: - break; - default: - count = 0; - break; + // loop forever + for (;;) { + // input + new_time = time(NULL); + // returns 0 bytes on timeout + pdu_len = datalink_receive(&src, &Rx_Buf[0], MAX_MPDU, timeout); + + // process + if (pdu_len) { + npdu_handler(&src, &Rx_Buf[0], pdu_len); + } + if (new_time > start_time) { + tsm_timer_milliseconds(new_time - start_time * 1000); + start_time = new_time; + } + if (I_Am_Request) { + I_Am_Request = false; + iam_send(&Handler_Transmit_Buffer[0]); + } else if (Who_Is_Request) { + Who_Is_Request = false; + Send_WhoIs(-1, -1); + } + // output + // some round robin task switching + count++; + switch (count) { + case 1: + // used for testing, but kind of noisy on the network + //Read_Properties(); + break; + case 2: + break; + default: + count = 0; + break; + } + + // blink LEDs, Turn on or off outputs, etc } - // blink LEDs, Turn on or off outputs, etc - } - - return 0; + return 0; } diff --git a/bacnet-stack/ports/linux/net.h b/bacnet-stack/ports/linux/net.h index 51e892da..1afeabce 100644 --- a/bacnet-stack/ports/linux/net.h +++ b/bacnet-stack/ports/linux/net.h @@ -27,34 +27,34 @@ #define NET_H /* common unix sockets headers needed */ -#include /* basic system data types */ -#include /* timeval{} for select() */ -#include /* timespec{} for pselect() */ -#include /* sockaddr_in{} and other Internet defns */ -#include /* inet(3) functions */ -#include /* for nonblocking */ +#include /* basic system data types */ +#include /* timeval{} for select() */ +#include /* timespec{} for pselect() */ +#include /* sockaddr_in{} and other Internet defns */ +#include /* inet(3) functions */ +#include /* for nonblocking */ #include #include #include #include #include #include -#include /* for S_xxx file mode constants */ -#include /* for iovec{} and readv/writev */ +#include /* for S_xxx file mode constants */ +#include /* for iovec{} and readv/writev */ #include #include -#include /* for Unix domain sockets */ +#include /* for Unix domain sockets */ #ifdef HAVE_SYS_SELECT_H -# include /* for convenience */ +# include /* for convenience */ #endif #ifdef HAVE_POLL_H -# include /* for convenience */ +# include /* for convenience */ #endif #ifdef HAVE_STRINGS_H -# include /* for convenience */ +# include /* for convenience */ #endif /* Three headers are normally needed for socket/file ioctl's: diff --git a/bacnet-stack/ports/linux/rs485.c b/bacnet-stack/ports/linux/rs485.c index 3529e50e..6fb1619b 100644 --- a/bacnet-stack/ports/linux/rs485.c +++ b/bacnet-stack/ports/linux/rs485.c @@ -40,60 +40,54 @@ #include #include #include - + #include "mstp.h" // Transmits a Frame on the wire -void RS485_Send_Frame( - struct mstp_port_struct_t *mstp_port, // port specific data - uint8_t *buffer, // frame to send (up to 501 bytes of data) - uint16_t nbytes) // number of bytes of data (up to 501) +void RS485_Send_Frame(struct mstp_port_struct_t *mstp_port, // port specific data + uint8_t * buffer, // frame to send (up to 501 bytes of data) + uint16_t nbytes) // number of bytes of data (up to 501) { - // in order to avoid line contention - while (mstp_port->Turn_Around_Waiting) - { - // wait, yield, or whatever - } + // in order to avoid line contention + while (mstp_port->Turn_Around_Waiting) { + // wait, yield, or whatever + } - // Disable the receiver, and enable the transmit line driver. + // Disable the receiver, and enable the transmit line driver. - while (nbytes) - { - putc(*buffer,stderr); - buffer++; - nbytes--; - } + while (nbytes) { + putc(*buffer, stderr); + buffer++; + nbytes--; + } - // Wait until the final stop bit of the most significant CRC octet - // has been transmitted but not more than Tpostdrive. + // Wait until the final stop bit of the most significant CRC octet + // has been transmitted but not more than Tpostdrive. - // Disable the transmit line driver. + // Disable the transmit line driver. - return; + return; } // called by timer, interrupt(?) or other thread void RS485_Check_UART_Data(struct mstp_port_struct_t *mstp_port) { - if (mstp_port->ReceiveError == true) - { - // wait for state machine to clear this - } - // wait for state machine to read from the DataRegister - else if (mstp_port->DataAvailable == false) - { - // check for data + if (mstp_port->ReceiveError == true) { + // wait for state machine to clear this + } + // wait for state machine to read from the DataRegister + else if (mstp_port->DataAvailable == false) { + // check for data - // if error, - // ReceiveError = TRUE; - // return; + // if error, + // ReceiveError = TRUE; + // return; - mstp_port->DataRegister = 0; // FIXME: Get this data from UART or buffer + mstp_port->DataRegister = 0; // FIXME: Get this data from UART or buffer - // if data is ready, - // DataAvailable = TRUE; - // return; - } + // if data is ready, + // DataAvailable = TRUE; + // return; + } } - diff --git a/bacnet-stack/ports/rtos32/bip-init.c b/bacnet-stack/ports/rtos32/bip-init.c index 70415feb..b26e8e2a 100644 --- a/bacnet-stack/ports/rtos32/bip-init.c +++ b/bacnet-stack/ports/rtos32/bip-init.c @@ -37,174 +37,180 @@ #include "bip.h" #if (defined(BACDL_ETHERNET) || defined(BACDL_BIP)) -static int interface = SOCKET_ERROR; // SOCKET_ERROR means no open interface +static int interface = SOCKET_ERROR; // SOCKET_ERROR means no open interface #endif void bip_set_interface(char *ifname) { - /*dummy function - to make the demos compile easier */ + /*dummy function - to make the demos compile easier */ } #if (defined(BACDL_ETHERNET) || defined(BACDL_BIP)) /*-----------------------------------*/ -static void Error(const char * Msg) +static void Error(const char *Msg) { - int Code = WSAGetLastError(); + int Code = WSAGetLastError(); #ifdef HOST - printf("%s, error code: %i\n", Msg, Code); + printf("%s, error code: %i\n", Msg, Code); #else - printf("%s, error code: %s\n", Msg, xn_geterror_string(Code)); + printf("%s, error code: %s\n", Msg, xn_geterror_string(Code)); #endif - exit(1); + exit(1); } #ifndef HOST /*-----------------------------------*/ void InterfaceCleanup(void) { - if (interface != SOCKET_ERROR) - { - xn_interface_close(interface); - interface = SOCKET_ERROR; + if (interface != SOCKET_ERROR) { + xn_interface_close(interface); + interface = SOCKET_ERROR; #if DEVICE_ID == PRISM_PCMCIA_DEVICE - RTPCShutDown(); + RTPCShutDown(); #endif - } + } } #endif static void NetInitialize(void) // initialize the TCP/IP stack { - int Result; + int Result; #ifndef HOST - RTKernelInit(0); // get the kernel going + RTKernelInit(0); // get the kernel going - if (!RTKDebugVersion()) // switch of all diagnostics and error messages of RTIP-32 - xn_callbacks()->cb_wr_screen_string_fnc = NULL; + if (!RTKDebugVersion()) // switch of all diagnostics and error messages of RTIP-32 + xn_callbacks()->cb_wr_screen_string_fnc = NULL; - CLKSetTimerIntVal(10*1000); // 10 millisecond tick - RTKDelay(1); - RTCMOSSetSystemTime(); // get the right time-of-day + CLKSetTimerIntVal(10 * 1000); // 10 millisecond tick + RTKDelay(1); + RTCMOSSetSystemTime(); // get the right time-of-day #ifdef RTUSB_VER - RTURegisterCallback(USBAX172); // ax172 and ax772 drivers - RTURegisterCallback(USBAX772); - RTURegisterCallback(USBKeyboard); // support USB keyboards - FindUSBControllers(); // install USB host controllers - Sleep(2000); // give the USB stack time to enumerate devices + RTURegisterCallback(USBAX172); // ax172 and ax772 drivers + RTURegisterCallback(USBAX772); + RTURegisterCallback(USBKeyboard); // support USB keyboards + FindUSBControllers(); // install USB host controllers + Sleep(2000); // give the USB stack time to enumerate devices #endif #ifdef DHCP - XN_REGISTER_DHCP_CLI() // and optionally the DHCP client + XN_REGISTER_DHCP_CLI() // and optionally the DHCP client #endif + Result = xn_rtip_init(); // Initialize the RTIP stack + if (Result != 0) + Error("xn_rtip_init failed"); - Result = xn_rtip_init(); // Initialize the RTIP stack - if (Result != 0) - Error("xn_rtip_init failed"); + atexit(InterfaceCleanup); // make sure the driver is shut down properly + RTCallDebugger(RT_DBG_CALLRESET, (DWORD) exit, 0); // even if we get restarted by the debugger - atexit(InterfaceCleanup); // make sure the driver is shut down properly - RTCallDebugger(RT_DBG_CALLRESET, (DWORD)exit, 0); // even if we get restarted by the debugger - - Result = BIND_DRIVER(MINOR_0); // tell RTIP what Ethernet driver we want (see netcfg.h) - if (Result != 0) - Error("driver initialization failed"); + Result = BIND_DRIVER(MINOR_0); // tell RTIP what Ethernet driver we want (see netcfg.h) + if (Result != 0) + Error("driver initialization failed"); #if DEVICE_ID == PRISM_PCMCIA_DEVICE - // if this is a PCMCIA device, start the PCMCIA driver - if (RTPCInit(-1, 0, 2, NULL) == 0) - Error("No PCMCIA controller found"); + // if this is a PCMCIA device, start the PCMCIA driver + if (RTPCInit(-1, 0, 2, NULL) == 0) + Error("No PCMCIA controller found"); #endif - // Open the interface - interface = xn_interface_open_config(DEVICE_ID, MINOR_0, ED_IO_ADD, ED_IRQ, ED_MEM_ADD); - if (interface == SOCKET_ERROR) - Error("xn_interface_open_config failed"); - else - { - struct _iface_info ii; + // Open the interface + interface = + xn_interface_open_config(DEVICE_ID, MINOR_0, ED_IO_ADD, ED_IRQ, + ED_MEM_ADD); + if (interface == SOCKET_ERROR) + Error("xn_interface_open_config failed"); + else { + struct _iface_info ii; #ifdef BACDL_ETHERNET - BACNET_ADDRESS my_address; - unsigned i; + BACNET_ADDRESS my_address; + unsigned i; #endif - xn_interface_info(interface, &ii); - printf("Interface opened, MAC address: %02x-%02x-%02x-%02x-%02x-%02x\n", - ii.my_ethernet_address[0], ii.my_ethernet_address[1], ii.my_ethernet_address[2], - ii.my_ethernet_address[3], ii.my_ethernet_address[4], ii.my_ethernet_address[5]); + xn_interface_info(interface, &ii); + printf + ("Interface opened, MAC address: %02x-%02x-%02x-%02x-%02x-%02x\n", + ii.my_ethernet_address[0], ii.my_ethernet_address[1], + ii.my_ethernet_address[2], ii.my_ethernet_address[3], + ii.my_ethernet_address[4], ii.my_ethernet_address[5]); #ifdef BACDL_ETHERNET - for (i = 0; i < 6; i++) -{ - my_address.mac[i] = ii.my_ethernet_address[i]; -} - ethernet_set_my_address(&my_address); + for (i = 0; i < 6; i++) { + my_address.mac[i] = ii.my_ethernet_address[i]; + } + ethernet_set_my_address(&my_address); #endif - } + } #if DEVICE_ID == PRISM_PCMCIA_DEVICE || DEVICE_ID == PRISM_DEVICE - xn_wlan_setup(interface, // iface_no: value returned by xn_interface_open_config() - "network name", // SSID : network name set in the access point - "station name", // Name : name of this node - 0, // Channel : 0 for access points, 1..14 for ad-hoc - 0, // KeyIndex: 0 .. 3 - "12345", // WEP Key : key to use (5 or 13 bytes) - 0); // Flags : see manual and Wlanapi.h for details - Sleep(1000); // wireless devices need a little time before they can be used -#endif // WLAN device + xn_wlan_setup(interface, // iface_no: value returned by xn_interface_open_config() + "network name", // SSID : network name set in the access point + "station name", // Name : name of this node + 0, // Channel : 0 for access points, 1..14 for ad-hoc + 0, // KeyIndex: 0 .. 3 + "12345", // WEP Key : key to use (5 or 13 bytes) + 0); // Flags : see manual and Wlanapi.h for details + Sleep(1000); // wireless devices need a little time before they can be used +#endif // WLAN device -#if defined(AUTO_IP) // use xn_autoip() to get an IP address - Result = xn_autoip(interface, MinIP, MaxIP, NetMask, TargetIP); - if (Result == SOCKET_ERROR) - Error("xn_autoip failed"); - else -{ - printf("Auto-assigned IP address %i.%i.%i.%i\n", TargetIP[0], TargetIP[1], TargetIP[2], TargetIP[3]); - // define default gateway and DNS server - xn_rt_add(RT_DEFAULT, ip_ffaddr, DefaultGateway, 1, interface, RT_INF); - xn_set_server_list((DWORD*)DNSServer, 1); -} -#elif defined(DHCP) // use DHCP -{ - DHCP_param param[] = {{SUBNET_MASK, 1}, {DNS_OP, 1}, {ROUTER_OPTION, 1}}; - DHCP_session DS; - DHCP_conf DC; +#if defined(AUTO_IP) // use xn_autoip() to get an IP address + Result = xn_autoip(interface, MinIP, MaxIP, NetMask, TargetIP); + if (Result == SOCKET_ERROR) + Error("xn_autoip failed"); + else { + printf("Auto-assigned IP address %i.%i.%i.%i\n", TargetIP[0], + TargetIP[1], TargetIP[2], TargetIP[3]); + // define default gateway and DNS server + xn_rt_add(RT_DEFAULT, ip_ffaddr, DefaultGateway, 1, interface, + RT_INF); + xn_set_server_list((DWORD *) DNSServer, 1); + } +#elif defined(DHCP) // use DHCP + { + DHCP_param param[] = { {SUBNET_MASK, 1} + , {DNS_OP, 1} + , {ROUTER_OPTION, 1} + }; + DHCP_session DS; + DHCP_conf DC; - xn_init_dhcp_conf(&DC); // load default DHCP options - DC.plist = param; // add MASK, DNS, and gateway options - DC.plist_entries = sizeof(param) / sizeof(param[0]); - printf("Contacting DHCP server, please wait...\n"); - Result = xn_dhcp(interface, &DS, &DC); // contact DHCP server - if (Result == SOCKET_ERROR) - Error("xn_dhcp failed"); - memcpy(TargetIP, DS.client_ip, 4); - printf("My IP address is: %i.%i.%i.%i\n", TargetIP[0], TargetIP[1], TargetIP[2], TargetIP[3]); -} + xn_init_dhcp_conf(&DC); // load default DHCP options + DC.plist = param; // add MASK, DNS, and gateway options + DC.plist_entries = sizeof(param) / sizeof(param[0]); + printf("Contacting DHCP server, please wait...\n"); + Result = xn_dhcp(interface, &DS, &DC); // contact DHCP server + if (Result == SOCKET_ERROR) + Error("xn_dhcp failed"); + memcpy(TargetIP, DS.client_ip, 4); + printf("My IP address is: %i.%i.%i.%i\n", TargetIP[0], TargetIP[1], + TargetIP[2], TargetIP[3]); + } #else - // Set the IP address and interface - printf("Using static IP address %i.%i.%i.%i\n", TargetIP[0], TargetIP[1], TargetIP[2], TargetIP[3]); - Result = xn_set_ip(interface, TargetIP, NetMask); - // define default gateway and DNS server - xn_rt_add(RT_DEFAULT, ip_ffaddr, DefaultGateway, 1, interface, RT_INF); - xn_set_server_list((DWORD*)DNSServer, 1); + // Set the IP address and interface + printf("Using static IP address %i.%i.%i.%i\n", TargetIP[0], + TargetIP[1], TargetIP[2], TargetIP[3]); + Result = xn_set_ip(interface, TargetIP, NetMask); + // define default gateway and DNS server + xn_rt_add(RT_DEFAULT, ip_ffaddr, DefaultGateway, 1, interface, RT_INF); + xn_set_server_list((DWORD *) DNSServer, 1); #endif -#else // HOST defined, run on Windows +#else // HOST defined, run on Windows - WSADATA wd; - Result = WSAStartup(0x0101, &wd); + WSADATA wd; + Result = WSAStartup(0x0101, &wd); #endif - if (Result != 0) - Error("TCP/IP stack initialization failed"); + if (Result != 0) + Error("TCP/IP stack initialization failed"); } #endif bool bip_init(void) { - int rv = 0; // return from socket lib calls - struct sockaddr_in sin = {-1}; + int rv = 0; // return from socket lib calls + struct sockaddr_in sin = { -1 }; int value = 1; int sock_fd = -1; @@ -212,7 +218,7 @@ bool bip_init(void) bip_set_address(TargetIP[0], TargetIP[1], TargetIP[2], TargetIP[3]); - // FIXME: + // FIXME: #if 0 bip_set_address(NetMask[0], NetMask[1], NetMask[2], NetMask[3]); extern unsigned long bip_get_addr(void); @@ -237,14 +243,13 @@ bool bip_init(void) sin.sin_addr.s_addr = htonl(INADDR_ANY); sin.sin_port = htons(bip_get_port()); memset(&(sin.sin_zero), '\0', 8); - rv = bind(sock_fd, - (const struct sockaddr*)&sin, sizeof(struct sockaddr)); - if (rv < 0) - { + rv = bind(sock_fd, + (const struct sockaddr *) &sin, sizeof(struct sockaddr)); + if (rv < 0) { close(sock_fd); bip_set_socket(-1); return false; } - return true; + return true; } diff --git a/bacnet-stack/ports/rtos32/ethernet.c b/bacnet-stack/ports/rtos32/ethernet.c index 7c25398d..6ba22e98 100644 --- a/bacnet-stack/ports/rtos32/ethernet.c +++ b/bacnet-stack/ports/rtos32/ethernet.c @@ -25,8 +25,8 @@ #include // for standard integer types uint8_t etc. #include // for the standard bool type. -#include // for the standard bool type. -#include // for the standard bool type. +#include // for the standard bool type. +#include // for the standard bool type. #include #include #include @@ -40,6 +40,7 @@ uint8_t Ethernet_Broadcast[MAX_MAC_LEN] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }; // commonly used empty address for ethernet quick compare uint8_t Ethernet_Empty_MAC[MAX_MAC_LEN] = { 0, 0, 0, 0, 0, 0 }; + // my local device data - MAC address uint8_t Ethernet_MAC_Address[MAX_MAC_LEN] = { 0, 0, 0, 0, 0, 0 }; @@ -49,45 +50,44 @@ static struct sockaddr Ethernet_Address = { 0 }; bool ethernet_valid(void) { - return (Ethernet_Socket != -1); + return (Ethernet_Socket != -1); } void ethernet_cleanup(void) { - if (ethernet_valid()) - closesocket(Ethernet_Socket); - Ethernet_Socket = -1; + if (ethernet_valid()) + closesocket(Ethernet_Socket); + Ethernet_Socket = -1; - return; + return; } bool ethernet_init(char *interface_name) { - int value = 1; - - (void)interface_name; + int value = 1; + + (void) interface_name; // setup the socket Ethernet_Socket = socket(AF_INET, SOCK_RAW, 0); //Ethernet_Socket = socket(AF_INET, SOCK_STREAM, 0); if (Ethernet_Socket < 0) - fprintf(stderr,"ethernet: failed to bind to socket!\r\n"); + fprintf(stderr, "ethernet: failed to bind to socket!\r\n"); Ethernet_Address.sa_family = AF_INET; - memset(Ethernet_Address.sa_data,0,sizeof(Ethernet_Address.sa_data)); - if (bind(Ethernet_Socket, - &Ethernet_Address, sizeof(Ethernet_Address)) == SOCKET_ERROR) - fprintf(stderr,"ethernet: failed to bind to socket!\r\n"); + memset(Ethernet_Address.sa_data, 0, sizeof(Ethernet_Address.sa_data)); + if (bind(Ethernet_Socket, + &Ethernet_Address, sizeof(Ethernet_Address)) == SOCKET_ERROR) + fprintf(stderr, "ethernet: failed to bind to socket!\r\n"); //setsockopt(Ethernet_Socket,SOL_SOCKET,SO_802_2,(char *)&value,sizeof(value)); - return ethernet_valid(); + return ethernet_valid(); } /* function to send a packet out the 802.2 socket */ /* returns bytes sent on success, negative number on failure */ -int ethernet_send( - BACNET_ADDRESS *dest, // destination address - BACNET_ADDRESS *src, // source address - uint8_t *pdu, // any data to be sent - may be null - unsigned pdu_len) // number of bytes of data +int ethernet_send(BACNET_ADDRESS * dest, // destination address + BACNET_ADDRESS * src, // source address + uint8_t * pdu, // any data to be sent - may be null + unsigned pdu_len) // number of bytes of data { int bytes = 0; uint8_t mtu[MAX_MPDU] = { 0 }; @@ -95,100 +95,86 @@ int ethernet_send( int i = 0; // don't waste time if the socket is not valid - if (Ethernet_Socket < 0) - { + if (Ethernet_Socket < 0) { fprintf(stderr, "ethernet: 802.2 socket is invalid!\n"); return -1; } /* load destination ethernet MAC address */ - if (dest->mac_len == 6) - { - for (i = 0; i < 6; i++) - { - mtu[mtu_len] = dest->mac[i]; - mtu_len++; - } - } - else - { + if (dest->mac_len == 6) { + for (i = 0; i < 6; i++) { + mtu[mtu_len] = dest->mac[i]; + mtu_len++; + } + } else { fprintf(stderr, "ethernet: invalid destination MAC address!\n"); return -2; } /* load source ethernet MAC address */ - if (src->mac_len == 6) - { - for (i = 0; i < 6; i++) - { - mtu[mtu_len] = src->mac[i]; - mtu_len++; - } - } - else - { + if (src->mac_len == 6) { + for (i = 0; i < 6; i++) { + mtu[mtu_len] = src->mac[i]; + mtu_len++; + } + } else { fprintf(stderr, "ethernet: invalid source MAC address!\n"); return -3; } - if ((14 + 3 + pdu_len) > MAX_MPDU) - { + if ((14 + 3 + pdu_len) > MAX_MPDU) { fprintf(stderr, "ethernet: PDU is too big to send!\n"); return -4; } /* packet length */ - mtu_len += encode_unsigned16(&mtu[12], - 3 /*DSAP,SSAP,LLC*/ + pdu_len); + mtu_len += encode_unsigned16(&mtu[12], + 3 /*DSAP,SSAP,LLC */ + pdu_len); // Logical PDU portion - mtu[mtu_len++] = 0x82; /* DSAP for BACnet */ - mtu[mtu_len++] = 0x82; /* SSAP for BACnet */ - mtu[mtu_len++] = 0x03; /* Control byte in header */ + mtu[mtu_len++] = 0x82; /* DSAP for BACnet */ + mtu[mtu_len++] = 0x82; /* SSAP for BACnet */ + mtu[mtu_len++] = 0x03; /* Control byte in header */ memcpy(&mtu[mtu_len], pdu, pdu_len); mtu_len += pdu_len; - + /* Send the packet */ - bytes = - send(Ethernet_Socket, (const char *)&mtu, mtu_len, 0); + bytes = send(Ethernet_Socket, (const char *) &mtu, mtu_len, 0); /* did it get sent? */ if (bytes < 0) - fprintf(stderr,"ethernet: Error sending packet: %s\n", - strerror(errno)); - + fprintf(stderr, "ethernet: Error sending packet: %s\n", + strerror(errno)); + return bytes; } /* function to send a packet out the 802.2 socket */ /* returns bytes sent on success, negative number on failure */ -int ethernet_send_pdu( - BACNET_ADDRESS *dest, // destination address - uint8_t *pdu, // any data to be sent - may be null - unsigned pdu_len) // number of bytes of data +int ethernet_send_pdu(BACNET_ADDRESS * dest, // destination address + uint8_t * pdu, // any data to be sent - may be null + unsigned pdu_len) // number of bytes of data { - int i = 0; // counter - BACNET_ADDRESS src = {0}; // source address - - for (i = 0; i < 6; i++) - { - src.mac[i] = Ethernet_MAC_Address[i]; - src.mac_len++; - } - /* function to send a packet out the 802.2 socket */ - /* returns 1 on success, 0 on failure */ - return ethernet_send(dest, // destination address - &src, // source address - pdu, // any data to be sent - may be null - pdu_len); // number of bytes of data + int i = 0; // counter + BACNET_ADDRESS src = { 0 }; // source address + + for (i = 0; i < 6; i++) { + src.mac[i] = Ethernet_MAC_Address[i]; + src.mac_len++; + } + /* function to send a packet out the 802.2 socket */ + /* returns 1 on success, 0 on failure */ + return ethernet_send(dest, // destination address + &src, // source address + pdu, // any data to be sent - may be null + pdu_len); // number of bytes of data } // receives an 802.2 framed packet // returns the number of octets in the PDU, or zero on failure -uint16_t ethernet_receive( - BACNET_ADDRESS *src, // source address - uint8_t *pdu, // PDU data - uint16_t max_pdu, // amount of space available in the PDU - unsigned timeout) // number of milliseconds to wait for a packet +uint16_t ethernet_receive(BACNET_ADDRESS * src, // source address + uint8_t * pdu, // PDU data + uint16_t max_pdu, // amount of space available in the PDU + unsigned timeout) // number of milliseconds to wait for a packet { int received_bytes; - uint8_t buf[MAX_MPDU] = {0}; // data - uint16_t pdu_len = 0; // return value + uint8_t buf[MAX_MPDU] = { 0 }; // data + uint16_t pdu_len = 0; // return value fd_set read_fds; int max; struct timeval select_timeout; @@ -200,14 +186,11 @@ uint16_t ethernet_receive( /* we could just use a non-blocking socket, but that consumes all the CPU time. We can use a timeout; it is only supported as a select. */ - if (timeout >= 1000) - { + if (timeout >= 1000) { select_timeout.tv_sec = timeout / 1000; - select_timeout.tv_usec = - 1000 * (timeout - select_timeout.tv_sec * 1000); - } - else - { + select_timeout.tv_usec = + 1000 * (timeout - select_timeout.tv_sec * 1000); + } else { select_timeout.tv_sec = 0; select_timeout.tv_usec = 1000 * timeout; } @@ -216,7 +199,8 @@ uint16_t ethernet_receive( max = Ethernet_Socket; if (select(max + 1, &read_fds, NULL, NULL, &select_timeout) > 0) - received_bytes = recv(Ethernet_Socket, (char *)&buf[0], MAX_MPDU, 0); + received_bytes = + recv(Ethernet_Socket, (char *) &buf[0], MAX_MPDU, 0); else return 0; @@ -226,14 +210,15 @@ uint16_t ethernet_receive( // using O_NONBLOCK and no data // was immediately available for reading. if (errno != EAGAIN) - fprintf(stderr,"ethernet: Read error in receiving packet: %s\n", + fprintf(stderr, + "ethernet: Read error in receiving packet: %s\n", strerror(errno)); return 0; } if (received_bytes == 0) - return 0; - + return 0; + /* the signature of an 802.2 BACnet packet */ if ((buf[14] != 0x82) && (buf[15] != 0x82)) { //fprintf(stderr,"ethernet: Non-BACnet packet\n"); @@ -245,108 +230,95 @@ uint16_t ethernet_receive( // check destination address for when // the Ethernet card is in promiscious mode - if ((memcmp(&buf[0], Ethernet_MAC_Address,6) != 0) - && (memcmp(&buf[0], Ethernet_Broadcast, 6) != 0)) - { + if ((memcmp(&buf[0], Ethernet_MAC_Address, 6) != 0) + && (memcmp(&buf[0], Ethernet_Broadcast, 6) != 0)) { //fprintf(stderr, "ethernet: This packet isn't for us\n"); return 0; } - (void)decode_unsigned16(&buf[12],&pdu_len); + (void) decode_unsigned16(&buf[12], &pdu_len); pdu_len -= 3 /* DSAP, SSAP, LLC Control */ ; // copy the buffer into the PDU if (pdu_len < max_pdu) - memmove(&pdu[0],&buf[17],pdu_len); + memmove(&pdu[0], &buf[17], pdu_len); // ignore packets that are too large // client should check my max apdu first else - pdu_len = 0; + pdu_len = 0; return pdu_len; } -void ethernet_get_my_address(BACNET_ADDRESS *my_address) +void ethernet_get_my_address(BACNET_ADDRESS * my_address) { - int i = 0; - - my_address->mac_len = 0; - for (i = 0; i < 6; i++) - { - my_address->mac[i] = Ethernet_MAC_Address[i]; - my_address->mac_len++; - } - my_address->net = 0; // local only, no routing - my_address->len = 0; - for (i = 0; i < MAX_MAC_LEN; i++) - { - my_address->adr[i] = 0; - } + int i = 0; - return; + my_address->mac_len = 0; + for (i = 0; i < 6; i++) { + my_address->mac[i] = Ethernet_MAC_Address[i]; + my_address->mac_len++; + } + my_address->net = 0; // local only, no routing + my_address->len = 0; + for (i = 0; i < MAX_MAC_LEN; i++) { + my_address->adr[i] = 0; + } + + return; } -void ethernet_set_my_address(BACNET_ADDRESS *my_address) +void ethernet_set_my_address(BACNET_ADDRESS * my_address) { - int i = 0; - - for (i = 0; i < 6; i++) - { - Ethernet_MAC_Address[i] = my_address->mac[i]; - } + int i = 0; - return; + for (i = 0; i < 6; i++) { + Ethernet_MAC_Address[i] = my_address->mac[i]; + } + + return; } -void ethernet_get_broadcast_address( - BACNET_ADDRESS *dest) // destination address +void ethernet_get_broadcast_address(BACNET_ADDRESS * dest) // destination address { - int i = 0; // counter - - if (dest) - { - for (i = 0; i < 6; i++) - { - dest->mac[i] = Ethernet_Broadcast[i]; - } - dest->mac_len = 6; - dest->net = BACNET_BROADCAST_NETWORK; - dest->len = 0; // denotes broadcast address - for (i = 0; i < MAX_MAC_LEN; i++) - { - dest->adr[i] = 0; - } - } + int i = 0; // counter - return; + if (dest) { + for (i = 0; i < 6; i++) { + dest->mac[i] = Ethernet_Broadcast[i]; + } + dest->mac_len = 6; + dest->net = BACNET_BROADCAST_NETWORK; + dest->len = 0; // denotes broadcast address + for (i = 0; i < MAX_MAC_LEN; i++) { + dest->adr[i] = 0; + } + } + + return; } -void ethernet_debug_address( - const char *info, - BACNET_ADDRESS *dest) +void ethernet_debug_address(const char *info, BACNET_ADDRESS * dest) { - int i = 0; // counter + int i = 0; // counter - if (info) - fprintf(stderr,"%s",info); - if (dest) - { - fprintf(stderr,"Address:\n"); - fprintf(stderr," MAC Length=%d\n",dest->mac_len); - fprintf(stderr," MAC Address="); - for (i = 0; i < MAX_MAC_LEN; i++) - { - fprintf(stderr,"%02X ",(unsigned)dest->mac[i]); + if (info) + fprintf(stderr, "%s", info); + if (dest) { + fprintf(stderr, "Address:\n"); + fprintf(stderr, " MAC Length=%d\n", dest->mac_len); + fprintf(stderr, " MAC Address="); + for (i = 0; i < MAX_MAC_LEN; i++) { + fprintf(stderr, "%02X ", (unsigned) dest->mac[i]); + } + fprintf(stderr, "\n"); + fprintf(stderr, " Net=%hu\n", dest->net); + fprintf(stderr, " Len=%d\n", dest->len); + fprintf(stderr, " Adr="); + for (i = 0; i < MAX_MAC_LEN; i++) { + fprintf(stderr, "%02X ", (unsigned) dest->adr[i]); + } + fprintf(stderr, "\n"); } - fprintf(stderr,"\n"); - fprintf(stderr," Net=%hu\n",dest->net); - fprintf(stderr," Len=%d\n",dest->len); - fprintf(stderr," Adr="); - for (i = 0; i < MAX_MAC_LEN; i++) - { - fprintf(stderr,"%02X ",(unsigned)dest->adr[i]); - } - fprintf(stderr,"\n"); - } - return; + return; } diff --git a/bacnet-stack/ports/rtos32/init.c b/bacnet-stack/ports/rtos32/init.c index 65cc0ef3..cf0a3f69 100644 --- a/bacnet-stack/ports/rtos32/init.c +++ b/bacnet-stack/ports/rtos32/init.c @@ -30,34 +30,33 @@ extern void RTEmuInit(void); #ifdef _MSC_VER - #define VOIDEXPORT _declspec(dllexport) void __cdecl +#define VOIDEXPORT _declspec(dllexport) void __cdecl #else - #define VOIDEXPORT void __export __cdecl +#define VOIDEXPORT void __export __cdecl #endif /* DISK SYSTEM */ -#ifdef DOC // include DiskOnChip driver - #include - #define RTF_MAX_FILES 16 // support for more open files (default is 8) - #define RTF_BUFFERS_IN_BSS // we do not need file I/O before the run-time - #include // system is initialized +#ifdef DOC // include DiskOnChip driver +#include +#define RTF_MAX_FILES 16 // support for more open files (default is 8) +#define RTF_BUFFERS_IN_BSS // we do not need file I/O before the run-time +#include // system is initialized //#define READ_HEAD_BUFFER_SIZE 2048+4 //static BYTE ReadAheadBuffer[READ_HEAD_BUFFER_SIZE]; - static RTFDrvFLPYData FLPYDriveAData = {0}; - static RTFDrvDOCData DOCDriveData = {0}; - static RTFDrvIDEData IDEDriveData = {0}; +static RTFDrvFLPYData FLPYDriveAData = { 0 }; +static RTFDrvDOCData DOCDriveData = { 0 }; +static RTFDrvIDEData IDEDriveData = { 0 }; - RTFDevice RTFDeviceList[] = - { +RTFDevice RTFDeviceList[] = { /* type,number,flags,driver,driverdata */ - { RTF_DEVICE_FLOPPY, 0, 0, &RTFDrvFloppy, &FLPYDriveAData}, - { RTF_DEVICE_FDISK , 0, 0, &RTFDrvDOC, &DOCDriveData}, - { RTF_DEVICE_FDISK , 0, 0, &RTFDrvIDE, &IDEDriveData}, - { 0 , 0, 0, NULL, NULL} - }; + {RTF_DEVICE_FLOPPY, 0, 0, &RTFDrvFloppy, &FLPYDriveAData}, + {RTF_DEVICE_FDISK, 0, 0, &RTFDrvDOC, &DOCDriveData}, + {RTF_DEVICE_FDISK, 0, 0, &RTFDrvIDE, &IDEDriveData}, + {0, 0, 0, NULL, NULL} +}; #endif /* END OF DISK SYSTEM */ @@ -67,14 +66,14 @@ extern void RTEmuInit(void); #define MAXOBJECTS 1024 #define MAXTYPES 32 -RTW32Handle RTHandleTable[MAXHANDLES] = {{0}}; -int RTHandleCount = MAXHANDLES; +RTW32Handle RTHandleTable[MAXHANDLES] = { {0} }; +int RTHandleCount = MAXHANDLES; -RTW32Object RTObjectTable[MAXOBJECTS] = {{0}}; -int RTObjectCount = MAXOBJECTS; +RTW32Object RTObjectTable[MAXOBJECTS] = { {0} }; +int RTObjectCount = MAXOBJECTS; -RTW32Types RTTypeTable[MAXTYPES] = {{0}}; -int RTTypeCount = MAXTYPES; +RTW32Types RTTypeTable[MAXTYPES] = { {0} }; +int RTTypeCount = MAXTYPES; #if 0 /* We can embed some files in the RTB file, like a binary @@ -85,44 +84,41 @@ int RTTypeCount = MAXTYPES; that here, as well as the LPT, console, and FAT. From RTFiles-32 manual, ch. 7, "Using RTFiles-32 with RTTarget-32" */ -RTFileSystem Console = -{ RT_FS_CONSOLE, 0, 0, &RTConsoleFileSystem }; +RTFileSystem Console = { RT_FS_CONSOLE, 0, 0, &RTConsoleFileSystem }; -RTFileSystem LPTFiles = -{ RT_FS_LPT_DEVICE, 0, 0, &RTLPTFileSystem }; +RTFileSystem LPTFiles = { RT_FS_LPT_DEVICE, 0, 0, &RTLPTFileSystem }; /* logical drive Z: can be used to access the RAM drive */ RTFileSystem RAMFiles = -{ RT_FS_FILE,1 << ('Z'-'A'), 0, &RTRAMFileSystem }; + { RT_FS_FILE, 1 << ('Z' - 'A'), 0, &RTRAMFileSystem }; /* logical drive A: through D: are reserved for FAT */ RTFileSystem FATFiles = -{ RT_FS_FILE | RT_FS_IS_DEFAULT, 0x0F, 0x03, &RTFilesFileSystem }; + { RT_FS_FILE | RT_FS_IS_DEFAULT, 0x0F, 0x03, &RTFilesFileSystem }; -RTFileSystem *RTFileSystemList[] = -{ - &Console, - &LPTFiles, - &RAMFiles, - &FATFiles, - NULL, +RTFileSystem *RTFileSystemList[] = { + &Console, + &LPTFiles, + &RAMFiles, + &FATFiles, + NULL, }; #endif /*-----------------------------------*/ VOIDEXPORT Init(void) { - (void)RTSetFlags(RT_MM_VIRTUAL, 1); // this is the better method - (void)RTCMOSExtendHeap(); // get as much memory as we can - RTCMOSSetSystemTime(); // get the right date and time - RTEmuInit(); // set up floating point emulation - // pizza - RTHaltCPL3 appears to cause problems with file handling - //RTIdleHandler = (void RTTAPI *)RTHaltCPL3; // low power when idle - // not needed with pre-emptive - //RTKTimeSlice(2); // allow same priority task switch - RTKConfig.Flags |= RF_PREEMPTIVE; // preemptive multitasking - RTKConfig.Flags |= RF_WIN32MUTEX_MUTEX; // Win32 mutexes are RTK32 mutexes - RTKConfig.Flags |= RF_FPCONTEXT; // saves floating point context for tasks - RTKConfig.HookedIRQs |= 1 << 1; // hook the keyboard IRQ - RTKConfig.DefaultTaskStackSize = 1024*8; // for Win32 task stacks req = 0 + (void) RTSetFlags(RT_MM_VIRTUAL, 1); // this is the better method + (void) RTCMOSExtendHeap(); // get as much memory as we can + RTCMOSSetSystemTime(); // get the right date and time + RTEmuInit(); // set up floating point emulation + // pizza - RTHaltCPL3 appears to cause problems with file handling + //RTIdleHandler = (void RTTAPI *)RTHaltCPL3; // low power when idle + // not needed with pre-emptive + //RTKTimeSlice(2); // allow same priority task switch + RTKConfig.Flags |= RF_PREEMPTIVE; // preemptive multitasking + RTKConfig.Flags |= RF_WIN32MUTEX_MUTEX; // Win32 mutexes are RTK32 mutexes + RTKConfig.Flags |= RF_FPCONTEXT; // saves floating point context for tasks + RTKConfig.HookedIRQs |= 1 << 1; // hook the keyboard IRQ + RTKConfig.DefaultTaskStackSize = 1024 * 8; // for Win32 task stacks req = 0 } diff --git a/bacnet-stack/ports/rtos32/main.c b/bacnet-stack/ports/rtos32/main.c index 25205a4b..ba216ee5 100644 --- a/bacnet-stack/ports/rtos32/main.c +++ b/bacnet-stack/ports/rtos32/main.c @@ -37,95 +37,82 @@ #include "net.h" // buffers used for transmit and receive -static uint8_t Rx_Buf[MAX_MPDU] = {0}; +static uint8_t Rx_Buf[MAX_MPDU] = { 0 }; + #ifdef BACDL_MSTP -volatile struct mstp_port_struct_t MSTP_Port; // port data +volatile struct mstp_port_struct_t MSTP_Port; // port data static uint8_t MSTP_MAC_Address = 0x05; // local MAC address #endif static void Init_Service_Handlers(void) { - // we need to handle who-is to support dynamic device binding - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_WHO_IS, - WhoIsHandler); - // set the handler for all the services we don't implement - // It is required to send the proper reject message... - apdu_set_unrecognized_service_handler_handler( - UnrecognizedServiceHandler); - // we must implement read property - it's required! - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - ReadPropertyHandler); - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_WRITE_PROPERTY, - WritePropertyHandler); + // we need to handle who-is to support dynamic device binding + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_WHO_IS, WhoIsHandler); + // set the handler for all the services we don't implement + // It is required to send the proper reject message... + apdu_set_unrecognized_service_handler_handler + (UnrecognizedServiceHandler); + // we must implement read property - it's required! + apdu_set_confirmed_handler(SERVICE_CONFIRMED_READ_PROPERTY, + ReadPropertyHandler); + apdu_set_confirmed_handler(SERVICE_CONFIRMED_WRITE_PROPERTY, + WritePropertyHandler); } int main(int argc, char *argv[]) { - BACNET_ADDRESS src = {0}; // address where message came from - uint16_t pdu_len = 0; - unsigned timeout = 100; // milliseconds + BACNET_ADDRESS src = { 0 }; // address where message came from + uint16_t pdu_len = 0; + unsigned timeout = 100; // milliseconds - (void)argc; - (void)argv; - Device_Set_Object_Instance_Number(126); - Init_Service_Handlers(); - // init the physical layer - #ifdef BACDL_BIP - if (!bip_init()) - return 1; - #endif - #ifdef BACDL_ETHERNET - if (!ethernet_init(NULL)) - return 1; - #endif - #ifdef BACDL_MSTP - RS485_Initialize(); - MSTP_Init(&MSTP_Port,MSTP_MAC_Address); - #endif + (void) argc; + (void) argv; + Device_Set_Object_Instance_Number(126); + Init_Service_Handlers(); + // init the physical layer +#ifdef BACDL_BIP + if (!bip_init()) + return 1; +#endif +#ifdef BACDL_ETHERNET + if (!ethernet_init(NULL)) + return 1; +#endif +#ifdef BACDL_MSTP + RS485_Initialize(); + MSTP_Init(&MSTP_Port, MSTP_MAC_Address); +#endif - - // loop forever - for (;;) - { - // input - #ifdef BACDL_MSTP - MSTP_Millisecond_Timer(&MSTP_Port); - // note: also called by RS-485 Receive ISR - RS485_Check_UART_Data(&MSTP_Port); - MSTP_Receive_Frame_FSM(&MSTP_Port); - #endif - #if (defined(BACDL_ETHERNET) || defined(BACDL_BIP)) - // returns 0 bytes on timeout - pdu_len = bacdl_receive( - &src, - &Rx_Buf[0], - MAX_MPDU, - timeout); - #endif + // loop forever + for (;;) { + // input +#ifdef BACDL_MSTP + MSTP_Millisecond_Timer(&MSTP_Port); + // note: also called by RS-485 Receive ISR + RS485_Check_UART_Data(&MSTP_Port); + MSTP_Receive_Frame_FSM(&MSTP_Port); +#endif - // process +#if (defined(BACDL_ETHERNET) || defined(BACDL_BIP)) + // returns 0 bytes on timeout + pdu_len = bacdl_receive(&src, &Rx_Buf[0], MAX_MPDU, timeout); +#endif - if (pdu_len) - { - npdu_handler( - &src, - &Rx_Buf[0], - pdu_len); + // process + + if (pdu_len) { + npdu_handler(&src, &Rx_Buf[0], pdu_len); + } + if (I_Am_Request) { + I_Am_Request = false; + Send_IAm(); + } + // output +#ifdef BACDL_MSTP + MSTP_Master_Node_FSM(&MSTP_Port); +#endif + + // blink LEDs, Turn on or off outputs, etc } - if (I_Am_Request) - { - I_Am_Request = false; - Send_IAm(); - } - // output - #ifdef BACDL_MSTP - MSTP_Master_Node_FSM(&MSTP_Port); - #endif - - // blink LEDs, Turn on or off outputs, etc - } } diff --git a/bacnet-stack/ports/rtos32/net.h b/bacnet-stack/ports/rtos32/net.h index 15b0298f..b339073f 100644 --- a/bacnet-stack/ports/rtos32/net.h +++ b/bacnet-stack/ports/rtos32/net.h @@ -35,17 +35,17 @@ #include #ifdef BACDL_BIP - #include "bip.h" - #ifndef HOST - #include "netcfg.h" - #include - #include - #include - #include - #else - #include - #endif - #define close closesocket +#include "bip.h" +#ifndef HOST +#include "netcfg.h" +#include +#include +#include +#include +#else +#include +#endif +#define close closesocket #endif #endif diff --git a/bacnet-stack/ports/rtos32/netcfg.h b/bacnet-stack/ports/rtos32/netcfg.h index 8068e6c9..5c63c8e9 100644 --- a/bacnet-stack/ports/rtos32/netcfg.h +++ b/bacnet-stack/ports/rtos32/netcfg.h @@ -31,74 +31,74 @@ // #define AUTO_IP // use xn_autoip() to get an IP address // #define DHCP // if you enable this, you must also link library dhcpc.lib -#if defined(AUTO_IP) // use xn_autoip() to get an IP address - static BYTE TargetIP[] = { 0, 0, 0, 0}; // will be filled at run-time - static BYTE NetMask[] = {255, 255, 255, 0}; - static BYTE MinIP[] = {192, 168, 1, 128}; - static BYTE MaxIP[] = {192, 168, 1, 255}; - static BYTE DefaultGateway[] = {192, 168, 1, 1}; // set to zero if not available or required - static BYTE DNSServer[] = {192, 168, 1, 1}; // ditto -#elif defined(DHCP) // use DHCP - #include - static BYTE TargetIP[] = { 0, 0, 0, 0}; // will be filled at run-time -#else // static IP address assignment (default) - static BYTE TargetIP[] = {192, 168, 0, 50}; - static BYTE NetMask[] = {255, 255, 255, 0}; - static BYTE DefaultGateway[] = {192, 168, 0, 1}; // set to zero if not available or required - static BYTE DNSServer[] = {192, 168, 0, 1}; // ditto +#if defined(AUTO_IP) // use xn_autoip() to get an IP address +static BYTE TargetIP[] = { 0, 0, 0, 0 }; // will be filled at run-time +static BYTE NetMask[] = { 255, 255, 255, 0 }; +static BYTE MinIP[] = { 192, 168, 1, 128 }; +static BYTE MaxIP[] = { 192, 168, 1, 255 }; +static BYTE DefaultGateway[] = { 192, 168, 1, 1 }; // set to zero if not available or required +static BYTE DNSServer[] = { 192, 168, 1, 1 }; // ditto +#elif defined(DHCP) // use DHCP +#include +static BYTE TargetIP[] = { 0, 0, 0, 0 }; // will be filled at run-time +#else // static IP address assignment (default) +static BYTE TargetIP[] = { 192, 168, 0, 50 }; +static BYTE NetMask[] = { 255, 255, 255, 0 }; +static BYTE DefaultGateway[] = { 192, 168, 0, 1 }; // set to zero if not available or required +static BYTE DNSServer[] = { 192, 168, 0, 1 }; // ditto #endif -#define DEVICE_ID DAVICOM_DEVICE // define your device type here +#define DEVICE_ID DAVICOM_DEVICE // define your device type here #ifndef DEVICE_ID - #error You must define Ethernet driver/resources and IP address/net mask here +#error You must define Ethernet driver/resources and IP address/net mask here #endif // The following values are ignored for PCI devices (the BIOS supplies // them), but they must be set correctly for ISA/PCMCIA systems and for // PCI devices if you do not have a BIOS -#define ED_IO_ADD 0x300 // I/O address of the device -#define ED_IRQ 5 // IRQ of the device -#define ED_MEM_ADD 0 // Memory Window (only some devices) +#define ED_IO_ADD 0x300 // I/O address of the device +#define ED_IRQ 5 // IRQ of the device +#define ED_MEM_ADD 0 // Memory Window (only some devices) // Define function to pull in the required driver #if DEVICE_ID == NE2000_DEVICE - #define BIND_DRIVER xn_bind_ne2000 +#define BIND_DRIVER xn_bind_ne2000 #elif DEVICE_ID == N83815_DEVICE - #define BIND_DRIVER xn_bind_n83815 +#define BIND_DRIVER xn_bind_n83815 #elif DEVICE_ID == TC90X_DEVICE - #define BIND_DRIVER xn_bind_tc90x +#define BIND_DRIVER xn_bind_tc90x #elif DEVICE_ID == SMC91C9X_DEVICE - #define BIND_DRIVER xn_bind_smc91c9x +#define BIND_DRIVER xn_bind_smc91c9x #elif DEVICE_ID == LANCE_DEVICE - #define BIND_DRIVER xn_bind_rtlance +#define BIND_DRIVER xn_bind_rtlance #elif DEVICE_ID == LANCE_ISA_DEVICE - #define BIND_DRIVER xn_bind_lance_isa +#define BIND_DRIVER xn_bind_lance_isa #elif DEVICE_ID == LAN_CS89X0_DEVICE - #define BIND_DRIVER xn_bind_cs +#define BIND_DRIVER xn_bind_cs #elif DEVICE_ID == I82559_DEVICE - #define BIND_DRIVER xn_bind_i82559 +#define BIND_DRIVER xn_bind_i82559 #elif DEVICE_ID == R8139_DEVICE - #define BIND_DRIVER xn_bind_r8139 +#define BIND_DRIVER xn_bind_r8139 #elif DEVICE_ID == DAVICOM_DEVICE - #define BIND_DRIVER xn_bind_davicom +#define BIND_DRIVER xn_bind_davicom #elif DEVICE_ID == RHINE_DEVICE - #define BIND_DRIVER xn_bind_rhine +#define BIND_DRIVER xn_bind_rhine #elif DEVICE_ID == AX172_DEVICE - #include // must also link Rtusb.lib and UsbInit.cpp - #define BIND_DRIVER xn_bind_ax172 +#include // must also link Rtusb.lib and UsbInit.cpp +#define BIND_DRIVER xn_bind_ax172 #elif DEVICE_ID == AX772_DEVICE - #include // must also link Rtusb.lib and UsbInit.cpp - #define BIND_DRIVER xn_bind_ax772 +#include // must also link Rtusb.lib and UsbInit.cpp +#define BIND_DRIVER xn_bind_ax772 #elif DEVICE_ID == PRISM_DEVICE - #include // must also link Wlan.lib - #define BIND_DRIVER xn_bind_prism +#include // must also link Wlan.lib +#define BIND_DRIVER xn_bind_prism #elif DEVICE_ID == PRISM_PCMCIA_DEVICE - #include - #include // must also link Wlan.lib - #define BIND_DRIVER xn_bind_prism_pcmcia +#include +#include // must also link Wlan.lib +#define BIND_DRIVER xn_bind_prism_pcmcia #else - #error Invalid DEVICE_ID value +#error Invalid DEVICE_ID value #endif diff --git a/bacnet-stack/ports/rtos32/rs485.c b/bacnet-stack/ports/rtos32/rs485.c index 15f81578..4081de2d 100644 --- a/bacnet-stack/ports/rtos32/rs485.c +++ b/bacnet-stack/ports/rtos32/rs485.c @@ -40,122 +40,115 @@ static int RS485_Port = COM2; /* baud rate */ static long RS485_Baud = 38400; /* io base address */ -static long RS485_Base = 0; +static long RS485_Base = 0; /* hardware IRQ number */ -static long RS485_IRQ_Number = 0; +static long RS485_IRQ_Number = 0; -static void RS485_Standard_Port_Settings(long port, long *pIRQ, long *pBase) +static void RS485_Standard_Port_Settings(long port, long *pIRQ, + long *pBase) { - switch (port) - { + switch (port) { case COM1: - *pBase = (long)0x3F8; - *pIRQ = 4L; - break; + *pBase = (long) 0x3F8; + *pIRQ = 4L; + break; case COM2: - *pBase = (long)0x2F8; - *pIRQ = 3L; - break; + *pBase = (long) 0x2F8; + *pIRQ = 3L; + break; case COM3: - *pBase = (long)0x3E8; - *pIRQ = 4L; - break; + *pBase = (long) 0x3E8; + *pIRQ = 4L; + break; case COM4: - *pBase = (long)0x2E8; - *pIRQ = 3L; - break; + *pBase = (long) 0x2E8; + *pIRQ = 3L; + break; default: - break; - } + break; + } } -static RS485_Open_Port( - int port, /* COM port number - COM1 = 0 */ - long baud, /* baud rate */ - unsigned base, /* io base address */ - int irq) /* hardware IRQ number */ -{ - /* setup the COM IO */ - SetIOBase(port, base); - SetIRQ(port, irq); +static RS485_Open_Port(int port, /* COM port number - COM1 = 0 */ + long baud, /* baud rate */ + unsigned base, /* io base address */ + int irq) +{ /* hardware IRQ number */ + /* setup the COM IO */ + SetIOBase(port, base); + SetIRQ(port, irq); - if (irq < 8) - RTKIRQTopPriority(irq,9); + if (irq < 8) + RTKIRQTopPriority(irq, 9); - InitPort(port, baud, PARITY_NONE, 1, 8); + InitPort(port, baud, PARITY_NONE, 1, 8); - if (HasFIFO(port)) - EnableFIFO(port,8); - EnableCOMInterrupt(port, 1024*4); + if (HasFIFO(port)) + EnableFIFO(port, 8); + EnableCOMInterrupt(port, 1024 * 4); - /* enable the 485 via the DTR pin */ - RS485_IO_ENABLE(port); - RS485_RECEIVE_ENABLE(port); + /* enable the 485 via the DTR pin */ + RS485_IO_ENABLE(port); + RS485_RECEIVE_ENABLE(port); - return; + return; } void RS485_Initialize(void) { - RS485_Standard_Port_Settings(RS485_Port, &RS485_IRQ_Number, &RS485_Base); - RS485_Open_Port(RS485_Port, RS485_Baud, RS485_Base, RS485_IRQ_Number); + RS485_Standard_Port_Settings(RS485_Port, &RS485_IRQ_Number, + &RS485_Base); + RS485_Open_Port(RS485_Port, RS485_Baud, RS485_Base, RS485_IRQ_Number); } -void RS485_Send_Frame( - volatile struct mstp_port_struct_t *mstp_port, // port specific data - uint8_t *buffer, // frame to send (up to 501 bytes of data) - uint16_t nbytes) // number of bytes of data (up to 501) +void RS485_Send_Frame(volatile struct mstp_port_struct_t *mstp_port, // port specific data + uint8_t * buffer, // frame to send (up to 501 bytes of data) + uint16_t nbytes) // number of bytes of data (up to 501) { - bool status = true; // return value + bool status = true; // return value - (void)mstp_port; - RS485_TRANSMIT_ENABLE(RS485_Port); - SendBlock(RS485_Port, (char *)buffer, nbytes); - /* need to wait at least 9600 baud * 512 bytes = 54mS */ - (void)WaitSendBufferEmpty(RS485_Port,MilliSecsToTicks(200)); - while (!(LineStatus(RS485_Port) & TX_SHIFT_EMPTY)) - RTKScheduler(); - RS485_RECEIVE_ENABLE(RS485_Port); + (void) mstp_port; + RS485_TRANSMIT_ENABLE(RS485_Port); + SendBlock(RS485_Port, (char *) buffer, nbytes); + /* need to wait at least 9600 baud * 512 bytes = 54mS */ + (void) WaitSendBufferEmpty(RS485_Port, MilliSecsToTicks(200)); + while (!(LineStatus(RS485_Port) & TX_SHIFT_EMPTY)) + RTKScheduler(); + RS485_RECEIVE_ENABLE(RS485_Port); - return; + return; } -void RS485_Check_UART_Data( - volatile struct mstp_port_struct_t *mstp_port) // port specific data +void RS485_Check_UART_Data(volatile struct mstp_port_struct_t *mstp_port) // port specific data { - COMData com_data = 0; /* byte from COM driver */ - unsigned timeout = 10; // milliseconds to wait for a character - Duration ticks; /* duration to wait for data */ + COMData com_data = 0; /* byte from COM driver */ + unsigned timeout = 10; // milliseconds to wait for a character + Duration ticks; /* duration to wait for data */ - if (mstp_port->ReceiveError) - { - // wait for state machine to clear this - } - // wait for state machine to read from the DataRegister - else if (!mstp_port->DataAvailable) - { - // check for data - ticks = MilliSecsToTicks(timeout); - if (!ticks) - ticks = 1; - if (RTKGetTimed(ReceiveBuffer[RS485_Port],&com_data,ticks)) - { - // if error, - if (com_data & (COM_OVERRUN << 8)) - mstp_port->ReceiveError = true; - else if (com_data & (COM_FRAME << 8)) - mstp_port->ReceiveError = true; - else - { - mstp_port->DataRegister = com_data & 0x00FF; - mstp_port->DataAvailable = true; - } + if (mstp_port->ReceiveError) { + // wait for state machine to clear this + } + // wait for state machine to read from the DataRegister + else if (!mstp_port->DataAvailable) { + // check for data + ticks = MilliSecsToTicks(timeout); + if (!ticks) + ticks = 1; + if (RTKGetTimed(ReceiveBuffer[RS485_Port], &com_data, ticks)) { + // if error, + if (com_data & (COM_OVERRUN << 8)) + mstp_port->ReceiveError = true; + else if (com_data & (COM_FRAME << 8)) + mstp_port->ReceiveError = true; + else { + mstp_port->DataRegister = com_data & 0x00FF; + mstp_port->DataAvailable = true; + } + } } - } } void RS485_Process_Tx_Message(void) { // nothing to do } - diff --git a/bacnet-stack/ports/rtos32/stdbool.h b/bacnet-stack/ports/rtos32/stdbool.h index 29b9a5e4..ba9e265d 100644 --- a/bacnet-stack/ports/rtos32/stdbool.h +++ b/bacnet-stack/ports/rtos32/stdbool.h @@ -4,25 +4,25 @@ // C99 Boolean types for compilers without C99 support #ifndef __cplusplus - typedef int _Bool; - #ifndef bool - #define bool _Bool - #endif - #ifndef true - #define true 1 - #endif - #ifndef false - #define false 0 - #endif - #define __bool_true_false_are_defined 1 +typedef int _Bool; +#ifndef bool +#define bool _Bool +#endif +#ifndef true +#define true 1 +#endif +#ifndef false +#define false 0 +#endif +#define __bool_true_false_are_defined 1 #endif #ifndef FALSE - #define FALSE 0 +#define FALSE 0 #endif #ifndef TRUE - #define TRUE 1 +#define TRUE 1 #endif #endif diff --git a/bacnet-stack/ports/rtos32/stdint.h b/bacnet-stack/ports/rtos32/stdint.h index 3615d7ea..8a674eda 100644 --- a/bacnet-stack/ports/rtos32/stdint.h +++ b/bacnet-stack/ports/rtos32/stdint.h @@ -6,14 +6,14 @@ #include -typedef unsigned char uint8_t; // 1 byte 0 to 255 -typedef signed char int8_t; // 1 byte -127 to 127 -typedef unsigned short uint16_t; // 2 bytes 0 to 65535 -typedef signed short int16_t; // 2 bytes -32767 to 32767 +typedef unsigned char uint8_t; // 1 byte 0 to 255 +typedef signed char int8_t; // 1 byte -127 to 127 +typedef unsigned short uint16_t; // 2 bytes 0 to 65535 +typedef signed short int16_t; // 2 bytes -32767 to 32767 //typedef unsigned short long uint24_t; // 3 bytes 0 to 16777215 -typedef unsigned long uint32_t; // 4 bytes 0 to 4294967295 -typedef signed long int32_t; // 4 bytes -2147483647 to 2147483647 +typedef unsigned long uint32_t; // 4 bytes 0 to 4294967295 +typedef signed long int32_t; // 4 bytes -2147483647 to 2147483647 // typedef signed long long int64_t; // typedef unsigned long long uint64_t; -#endif // STDINT_H +#endif // STDINT_H diff --git a/bacnet-stack/ports/win32/bip-init.c b/bacnet-stack/ports/win32/bip-init.c index fedc8f02..8a2733d7 100644 --- a/bacnet-stack/ports/win32/bip-init.c +++ b/bacnet-stack/ports/win32/bip-init.c @@ -37,8 +37,8 @@ #include #include -#include // for standard integer types uint8_t etc. -#include // for the standard bool type. +#include // for standard integer types uint8_t etc. +#include // for the standard bool type. #include "bacdcode.h" #include "bip.h" #include "net.h" @@ -46,60 +46,64 @@ /* To fill a need, we invent the gethostaddr() function. */ static long gethostaddr(void) { - struct hostent *host_ent; - char host_name[255]; + struct hostent *host_ent; + char host_name[255]; - if (gethostname(host_name, sizeof(host_name)) != 0) - return -1; - #ifdef BIP_DEBUG - printf("host name: %s\n",host_name); - #endif - if ((host_ent = gethostbyname(host_name)) == NULL) - return -1; + if (gethostname(host_name, sizeof(host_name)) != 0) + return -1; +#ifdef BIP_DEBUG + printf("host name: %s\n", host_name); +#endif + if ((host_ent = gethostbyname(host_name)) == NULL) + return -1; - return *(long *)host_ent->h_addr; + return *(long *) host_ent->h_addr; } static void set_broadcast_address(uint32_t net_address) { - long broadcast_address = 0; - long mask = 0; + long broadcast_address = 0; + long mask = 0; - /* Note: sometimes INADDR_BROADCAST does not let me get + /* Note: sometimes INADDR_BROADCAST does not let me get any unicast messages. Not sure why... */ - #if USE_INADDR - (void)net_address; - bip_set_broadcast_addr(INADDR_BROADCAST); - #else - if (IN_CLASSA(ntohl(net_address))) - broadcast_address = (ntohl(net_address) & ~IN_CLASSA_HOST) | IN_CLASSA_HOST; - else if (IN_CLASSB(ntohl(net_address))) - broadcast_address = (ntohl(net_address) & ~IN_CLASSB_HOST) | IN_CLASSB_HOST; - else if (IN_CLASSC(ntohl(net_address))) - broadcast_address = (ntohl(net_address) & ~IN_CLASSC_HOST) | IN_CLASSC_HOST; - else if (IN_CLASSD(ntohl(net_address))) - broadcast_address = (ntohl(net_address) & ~IN_CLASSD_HOST) | IN_CLASSD_HOST; - else - broadcast_address = INADDR_BROADCAST; - bip_set_broadcast_addr(htonl(broadcast_address)); - #endif +#if USE_INADDR + (void) net_address; + bip_set_broadcast_addr(INADDR_BROADCAST); +#else + if (IN_CLASSA(ntohl(net_address))) + broadcast_address = + (ntohl(net_address) & ~IN_CLASSA_HOST) | IN_CLASSA_HOST; + else if (IN_CLASSB(ntohl(net_address))) + broadcast_address = + (ntohl(net_address) & ~IN_CLASSB_HOST) | IN_CLASSB_HOST; + else if (IN_CLASSC(ntohl(net_address))) + broadcast_address = + (ntohl(net_address) & ~IN_CLASSC_HOST) | IN_CLASSC_HOST; + else if (IN_CLASSD(ntohl(net_address))) + broadcast_address = + (ntohl(net_address) & ~IN_CLASSD_HOST) | IN_CLASSD_HOST; + else + broadcast_address = INADDR_BROADCAST; + bip_set_broadcast_addr(htonl(broadcast_address)); +#endif } static void cleanup(void) { - WSACleanup(); + WSACleanup(); } void bip_set_interface(char *ifname) { - (void)ifname; - /* dummy function */ + (void) ifname; + /* dummy function */ } bool bip_init(void) { - int rv = 0; // return from socket lib calls - struct sockaddr_in sin = {-1}; + int rv = 0; // return from socket lib calls + struct sockaddr_in sin = { -1 }; int value = 1; int sock_fd = -1; int Result; @@ -109,63 +113,55 @@ bool bip_init(void) Result = WSAStartup((1 << 8) | 1, &wd); //Result = WSAStartup(MAKEWORD(2,2), &wd); - if (Result != 0) - { - Code = WSAGetLastError(); - printf("TCP/IP stack initialization failed, error code: %i\n", - Code); - exit(1); + if (Result != 0) { + Code = WSAGetLastError(); + printf("TCP/IP stack initialization failed, error code: %i\n", + Code); + exit(1); } atexit(cleanup); address.s_addr = gethostaddr(); - if (address.s_addr == (unsigned)-1) - { - Code = WSAGetLastError(); - printf("Get host address failed, error code: %i\n", - Code); - exit(1); + if (address.s_addr == (unsigned) -1) { + Code = WSAGetLastError(); + printf("Get host address failed, error code: %i\n", Code); + exit(1); } - #ifdef BIP_DEBUG - printf("host address: %s\n",inet_ntoa(address)); - #endif +#ifdef BIP_DEBUG + printf("host address: %s\n", inet_ntoa(address)); +#endif bip_set_addr(address.s_addr); set_broadcast_address(address.s_addr); /* assumes that the driver has already been initialized */ sock_fd = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP); bip_set_socket(sock_fd); - if (sock_fd < 0) - { - fprintf(stderr,"bip: failed to allocate a socket.\n"); - return false; + if (sock_fd < 0) { + fprintf(stderr, "bip: failed to allocate a socket.\n"); + return false; } - // Allow us to use the same socket for sending and receiving // This makes sure that the src port is correct when sending rv = setsockopt(sock_fd, SOL_SOCKET, SO_REUSEADDR, - (char *)&value, sizeof(value)); - if (rv < 0) - { - fprintf(stderr,"bip: failed to set REUSEADDR socket option.\n"); - close(sock_fd); - bip_set_socket(-1); - return false; + (char *) &value, sizeof(value)); + if (rv < 0) { + fprintf(stderr, "bip: failed to set REUSEADDR socket option.\n"); + close(sock_fd); + bip_set_socket(-1); + return false; } // allow us to send a broadcast rv = setsockopt(sock_fd, SOL_SOCKET, SO_BROADCAST, - (char *)&value, sizeof(value)); - if (rv < 0) - { - fprintf(stderr,"bip: failed to set BROADCAST socket option.\n"); - close(sock_fd); - bip_set_socket(-1); - return false; + (char *) &value, sizeof(value)); + if (rv < 0) { + fprintf(stderr, "bip: failed to set BROADCAST socket option.\n"); + close(sock_fd); + bip_set_socket(-1); + return false; } - // bind the socket to the local port number and IP address sin.sin_family = AF_INET; - #if USE_INADDR +#if USE_INADDR /* by setting sin.sin_addr.s_addr to INADDR_ANY, I am telling the IP stack to automatically fill in the IP address of the machine the process @@ -182,20 +178,18 @@ bool bip_init(void) Note: sometimes INADDR_ANY does not let me get any unicast messages. Not sure why... */ sin.sin_addr.s_addr = htonl(INADDR_ANY); - #else +#else /* or we could use the specific adapter address note: already in network byte order */ sin.sin_addr.s_addr = address.s_addr; - #endif +#endif sin.sin_port = htons(bip_get_port()); memset(&(sin.sin_zero), '\0', sizeof(sin.sin_zero)); rv = bind(sock_fd, - (const struct sockaddr*)&sin, sizeof(struct sockaddr)); - if (rv < 0) - { - fprintf(stderr,"bip: failed to bind to %s port %hd\n", - inet_ntoa(sin.sin_addr), - bip_get_port()); + (const struct sockaddr *) &sin, sizeof(struct sockaddr)); + if (rv < 0) { + fprintf(stderr, "bip: failed to bind to %s port %hd\n", + inet_ntoa(sin.sin_addr), bip_get_port()); close(sock_fd); bip_set_socket(-1); return false; @@ -203,4 +197,3 @@ bool bip_init(void) return true; } - diff --git a/bacnet-stack/ports/win32/main.c b/bacnet-stack/ports/win32/main.c index 8ed7c228..ec5d309a 100644 --- a/bacnet-stack/ports/win32/main.c +++ b/bacnet-stack/ports/win32/main.c @@ -29,7 +29,7 @@ #include #include #include -#include /* for kbhit and getch */ +#include /* for kbhit and getch */ #include "iam.h" #include "address.h" #include "config.h" @@ -43,262 +43,219 @@ #include "txbuf.h" // buffer used for receive -static uint8_t Rx_Buf[MAX_MPDU] = {0}; +static uint8_t Rx_Buf[MAX_MPDU] = { 0 }; + /* send a whois to see who is on the network */ static bool Who_Is_Request = true; static void Read_Properties(void) { - uint32_t device_id = 0; - bool status = false; - unsigned max_apdu = 0; - BACNET_ADDRESS src; - bool next_device = false; - static unsigned index = 0; - static unsigned property = 0; - /* list of required (and some optional) properties in the - Device Object - note: you could just loop through - all the properties in all the objects. */ - const int object_props[] = - { - PROP_OBJECT_IDENTIFIER, - PROP_OBJECT_NAME, - PROP_OBJECT_TYPE, - PROP_SYSTEM_STATUS, - PROP_VENDOR_NAME, - PROP_VENDOR_IDENTIFIER, - PROP_MODEL_NAME, - PROP_FIRMWARE_REVISION, - PROP_APPLICATION_SOFTWARE_VERSION, - PROP_PROTOCOL_VERSION, - PROP_PROTOCOL_CONFORMANCE_CLASS, - PROP_PROTOCOL_SERVICES_SUPPORTED, - PROP_PROTOCOL_OBJECT_TYPES_SUPPORTED, - PROP_MAX_APDU_LENGTH_ACCEPTED, - PROP_SEGMENTATION_SUPPORTED, - PROP_LOCAL_TIME, - PROP_LOCAL_DATE, - PROP_UTC_OFFSET, - PROP_DAYLIGHT_SAVINGS_STATUS, - PROP_APDU_SEGMENT_TIMEOUT, - PROP_APDU_TIMEOUT, - PROP_NUMBER_OF_APDU_RETRIES, - PROP_TIME_SYNCHRONIZATION_RECIPIENTS, - PROP_MAX_MASTER, - PROP_MAX_INFO_FRAMES, - PROP_DEVICE_ADDRESS_BINDING, - /* note: PROP_OBJECT_LIST is missing cause - we need to get it with an index method since - the list could be very large */ - /* some proprietary properties */ - 514,515, - /* end of list */ - -1 - }; + uint32_t device_id = 0; + bool status = false; + unsigned max_apdu = 0; + BACNET_ADDRESS src; + bool next_device = false; + static unsigned index = 0; + static unsigned property = 0; + /* list of required (and some optional) properties in the + Device Object + note: you could just loop through + all the properties in all the objects. */ + const int object_props[] = { + PROP_OBJECT_IDENTIFIER, + PROP_OBJECT_NAME, + PROP_OBJECT_TYPE, + PROP_SYSTEM_STATUS, + PROP_VENDOR_NAME, + PROP_VENDOR_IDENTIFIER, + PROP_MODEL_NAME, + PROP_FIRMWARE_REVISION, + PROP_APPLICATION_SOFTWARE_VERSION, + PROP_PROTOCOL_VERSION, + PROP_PROTOCOL_CONFORMANCE_CLASS, + PROP_PROTOCOL_SERVICES_SUPPORTED, + PROP_PROTOCOL_OBJECT_TYPES_SUPPORTED, + PROP_MAX_APDU_LENGTH_ACCEPTED, + PROP_SEGMENTATION_SUPPORTED, + PROP_LOCAL_TIME, + PROP_LOCAL_DATE, + PROP_UTC_OFFSET, + PROP_DAYLIGHT_SAVINGS_STATUS, + PROP_APDU_SEGMENT_TIMEOUT, + PROP_APDU_TIMEOUT, + PROP_NUMBER_OF_APDU_RETRIES, + PROP_TIME_SYNCHRONIZATION_RECIPIENTS, + PROP_MAX_MASTER, + PROP_MAX_INFO_FRAMES, + PROP_DEVICE_ADDRESS_BINDING, + /* note: PROP_OBJECT_LIST is missing cause + we need to get it with an index method since + the list could be very large */ + /* some proprietary properties */ + 514, 515, + /* end of list */ + -1 + }; - if (address_count()) - { - if (address_get_by_index(index, &device_id, &max_apdu, &src)) - { - if (object_props[property] < 0) - next_device = true; - else - { - status = Send_Read_Property_Request( - device_id, // destination device - OBJECT_DEVICE, - device_id, - object_props[property], - BACNET_ARRAY_ALL); - if (status) - property++; - } + if (address_count()) { + if (address_get_by_index(index, &device_id, &max_apdu, &src)) { + if (object_props[property] < 0) + next_device = true; + else { + status = Send_Read_Property_Request(device_id, // destination device + OBJECT_DEVICE, + device_id, object_props[property], BACNET_ARRAY_ALL); + if (status) + property++; + } + } else + next_device = true; + if (next_device) { + next_device = false; + index++; + if (index >= MAX_ADDRESS_CACHE) + index = 0; + property = 0; + } } - else - next_device = true; - if (next_device) - { - next_device = false; - index++; - if (index >= MAX_ADDRESS_CACHE) - index = 0; - property = 0; - } - } - return; + return; } -static void LocalIAmHandler( - uint8_t *service_request, - uint16_t service_len, - BACNET_ADDRESS *src) +static void LocalIAmHandler(uint8_t * service_request, + uint16_t service_len, BACNET_ADDRESS * src) { - int len = 0; - uint32_t device_id = 0; - unsigned max_apdu = 0; - int segmentation = 0; - uint16_t vendor_id = 0; + int len = 0; + uint32_t device_id = 0; + unsigned max_apdu = 0; + int segmentation = 0; + uint16_t vendor_id = 0; - (void)src; - (void)service_len; - len = iam_decode_service_request( - service_request, - &device_id, - &max_apdu, - &segmentation, - &vendor_id); - fprintf(stderr,"Received I-Am Request"); - if (len != -1) - { - fprintf(stderr," from %u!\n",device_id); - address_add(device_id, - max_apdu, - src); - } - else - fprintf(stderr,"!\n"); + (void) src; + (void) service_len; + len = iam_decode_service_request(service_request, + &device_id, &max_apdu, &segmentation, &vendor_id); + fprintf(stderr, "Received I-Am Request"); + if (len != -1) { + fprintf(stderr, " from %u!\n", device_id); + address_add(device_id, max_apdu, src); + } else + fprintf(stderr, "!\n"); - return; + return; } static void Init_Service_Handlers(void) { - // we need to handle who-is to support dynamic device binding - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_WHO_IS, - handler_who_is); - apdu_set_unconfirmed_handler( - SERVICE_UNCONFIRMED_I_AM, - LocalIAmHandler); + // we need to handle who-is to support dynamic device binding + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_WHO_IS, + handler_who_is); + apdu_set_unconfirmed_handler(SERVICE_UNCONFIRMED_I_AM, + LocalIAmHandler); - // set the handler for all the services we don't implement - // It is required to send the proper reject message... - apdu_set_unrecognized_service_handler_handler( - handler_unrecognized_service); - // we must implement read property - it's required! - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property); - apdu_set_confirmed_handler( - SERVICE_CONFIRMED_WRITE_PROPERTY, - handler_write_property); - // handle the data coming back from confirmed requests - apdu_set_confirmed_ack_handler( - SERVICE_CONFIRMED_READ_PROPERTY, - handler_read_property_ack); + // set the handler for all the services we don't implement + // It is required to send the proper reject message... + apdu_set_unrecognized_service_handler_handler + (handler_unrecognized_service); + // we must implement read property - it's required! + apdu_set_confirmed_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property); + apdu_set_confirmed_handler(SERVICE_CONFIRMED_WRITE_PROPERTY, + handler_write_property); + // handle the data coming back from confirmed requests + apdu_set_confirmed_ack_handler(SERVICE_CONFIRMED_READ_PROPERTY, + handler_read_property_ack); } -static void print_address( - char *name, - BACNET_ADDRESS *dest) // destination address +static void print_address(char *name, BACNET_ADDRESS * dest) // destination address { - int i = 0; // counter + int i = 0; // counter - if (dest) - { - printf("%s: ",name); - for (i = 0; i < dest->mac_len; i++) - { - printf("%02X",dest->mac[i]); + if (dest) { + printf("%s: ", name); + for (i = 0; i < dest->mac_len; i++) { + printf("%02X", dest->mac[i]); + } + printf("\n"); } - printf("\n"); - } } static void print_address_cache(void) { - int i,j; - BACNET_ADDRESS address; - uint32_t device_id = 0; - unsigned max_apdu = 0; + int i, j; + BACNET_ADDRESS address; + uint32_t device_id = 0; + unsigned max_apdu = 0; - fprintf(stderr,"Device\tMAC\tMaxAPDU\tNet\n"); - for (i = 0; i < MAX_ADDRESS_CACHE; i++) - { - if (address_get_by_index(i,&device_id, &max_apdu, &address)) - { - fprintf(stderr,"%u\t",device_id); - for (j = 0; j < address.mac_len; j++) - { - fprintf(stderr,"%02X",address.mac[j]); - } - fprintf(stderr,"\t"); - fprintf(stderr,"%hu\t",max_apdu); - fprintf(stderr,"%hu\n",address.net); + fprintf(stderr, "Device\tMAC\tMaxAPDU\tNet\n"); + for (i = 0; i < MAX_ADDRESS_CACHE; i++) { + if (address_get_by_index(i, &device_id, &max_apdu, &address)) { + fprintf(stderr, "%u\t", device_id); + for (j = 0; j < address.mac_len; j++) { + fprintf(stderr, "%02X", address.mac[j]); + } + fprintf(stderr, "\t"); + fprintf(stderr, "%hu\t", max_apdu); + fprintf(stderr, "%hu\n", address.net); + } } - } } int main(int argc, char *argv[]) { - BACNET_ADDRESS src = {0}; // address where message came from - uint16_t pdu_len = 0; - unsigned timeout = 100; // milliseconds - BACNET_ADDRESS my_address, broadcast_address; + BACNET_ADDRESS src = { 0 }; // address where message came from + uint16_t pdu_len = 0; + unsigned timeout = 100; // milliseconds + BACNET_ADDRESS my_address, broadcast_address; - (void)argc; - (void)argv; - Device_Set_Object_Instance_Number(124); - Init_Service_Handlers(); - // init the data link layer - /* configure standard BACnet/IP port */ - bip_set_port(0xBAC0); - if (!bip_init()) - return 1; + (void) argc; + (void) argv; + Device_Set_Object_Instance_Number(124); + Init_Service_Handlers(); + // init the data link layer + /* configure standard BACnet/IP port */ + bip_set_port(0xBAC0); + if (!bip_init()) + return 1; - datalink_get_broadcast_address(&broadcast_address); - print_address("Broadcast",&broadcast_address); - datalink_get_my_address(&my_address); - print_address("Address",&my_address); + datalink_get_broadcast_address(&broadcast_address); + print_address("Broadcast", &broadcast_address); + datalink_get_my_address(&my_address); + print_address("Address", &my_address); - printf("BACnet stack running...\n"); - // loop forever - for (;;) - { - // input + printf("BACnet stack running...\n"); + // loop forever + for (;;) { + // input - // returns 0 bytes on timeout - pdu_len = bip_receive( - &src, - &Rx_Buf[0], - MAX_MPDU, - timeout); + // returns 0 bytes on timeout + pdu_len = bip_receive(&src, &Rx_Buf[0], MAX_MPDU, timeout); - // process + // process - if (pdu_len) - { - npdu_handler( - &src, - &Rx_Buf[0], - pdu_len); - } - if (I_Am_Request) - { - I_Am_Request = false; - iam_send(&Handler_Transmit_Buffer[0]); - } else if (Who_Is_Request) - { - Who_Is_Request = false; - Send_WhoIs(-1,-1); - } - else - { - Read_Properties(); + if (pdu_len) { + npdu_handler(&src, &Rx_Buf[0], pdu_len); + } + if (I_Am_Request) { + I_Am_Request = false; + iam_send(&Handler_Transmit_Buffer[0]); + } else if (Who_Is_Request) { + Who_Is_Request = false; + Send_WhoIs(-1, -1); + } else { + Read_Properties(); + } + + // output + + // blink LEDs, Turn on or off outputs, etc + + /* wait for ESC from keyboard before quitting */ + if (kbhit() && (getch() == 0x1B)) + break; } - // output + print_address_cache(); - // blink LEDs, Turn on or off outputs, etc - - /* wait for ESC from keyboard before quitting */ - if (kbhit() && (getch() == 0x1B)) - break; - } - - print_address_cache(); - - return 0; + return 0; } diff --git a/bacnet-stack/ports/win32/stdbool.h b/bacnet-stack/ports/win32/stdbool.h index 29b9a5e4..ba9e265d 100644 --- a/bacnet-stack/ports/win32/stdbool.h +++ b/bacnet-stack/ports/win32/stdbool.h @@ -4,25 +4,25 @@ // C99 Boolean types for compilers without C99 support #ifndef __cplusplus - typedef int _Bool; - #ifndef bool - #define bool _Bool - #endif - #ifndef true - #define true 1 - #endif - #ifndef false - #define false 0 - #endif - #define __bool_true_false_are_defined 1 +typedef int _Bool; +#ifndef bool +#define bool _Bool +#endif +#ifndef true +#define true 1 +#endif +#ifndef false +#define false 0 +#endif +#define __bool_true_false_are_defined 1 #endif #ifndef FALSE - #define FALSE 0 +#define FALSE 0 #endif #ifndef TRUE - #define TRUE 1 +#define TRUE 1 #endif #endif diff --git a/bacnet-stack/ports/win32/stdint.h b/bacnet-stack/ports/win32/stdint.h index 3615d7ea..8a674eda 100644 --- a/bacnet-stack/ports/win32/stdint.h +++ b/bacnet-stack/ports/win32/stdint.h @@ -6,14 +6,14 @@ #include -typedef unsigned char uint8_t; // 1 byte 0 to 255 -typedef signed char int8_t; // 1 byte -127 to 127 -typedef unsigned short uint16_t; // 2 bytes 0 to 65535 -typedef signed short int16_t; // 2 bytes -32767 to 32767 +typedef unsigned char uint8_t; // 1 byte 0 to 255 +typedef signed char int8_t; // 1 byte -127 to 127 +typedef unsigned short uint16_t; // 2 bytes 0 to 65535 +typedef signed short int16_t; // 2 bytes -32767 to 32767 //typedef unsigned short long uint24_t; // 3 bytes 0 to 16777215 -typedef unsigned long uint32_t; // 4 bytes 0 to 4294967295 -typedef signed long int32_t; // 4 bytes -2147483647 to 2147483647 +typedef unsigned long uint32_t; // 4 bytes 0 to 4294967295 +typedef signed long int32_t; // 4 bytes -2147483647 to 2147483647 // typedef signed long long int64_t; // typedef unsigned long long uint64_t; -#endif // STDINT_H +#endif // STDINT_H