diff --git a/bacnet-stack/demo/handler/h_alarm_ack.c b/bacnet-stack/demo/handler/h_alarm_ack.c new file mode 100644 index 00000000..91481e41 --- /dev/null +++ b/bacnet-stack/demo/handler/h_alarm_ack.c @@ -0,0 +1,118 @@ +/************************************************************************** +* +* Copyright (C) 2005 Steve Karg +* +* Permission is hereby granted, free of charge, to any person obtaining +* a copy of this software and associated documentation files (the +* "Software"), to deal in the Software without restriction, including +* without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to +* permit persons to whom the Software is furnished to do so, subject to +* the following conditions: +* +* The above copyright notice and this permission notice shall be included +* in all copies or substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY +* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, +* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE +* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +* +*********************************************************************/ +#include +#include +#include +#include +#include +#include "config.h" +#include "txbuf.h" +#include "bacdef.h" +#include "bacdcode.h" +#include "apdu.h" +#include "npdu.h" +#include "abort.h" +#include "alarm_ack.h" +#include "handlers.h" + +void handler_alarm_ack( + uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, + BACNET_CONFIRMED_SERVICE_DATA * service_data) +{ + BACNET_ALARM_ACK_DATA data; + int len = 0; + int pdu_len = 0; + BACNET_NPDU_DATA npdu_data; + int bytes_sent = 0; + BACNET_ADDRESS my_address; + + /* encode the NPDU portion of the packet */ + datalink_get_my_address(&my_address); + npdu_encode_npdu_data(&npdu_data, false, MESSAGE_PRIORITY_NORMAL); + pdu_len = + npdu_encode_pdu(&Handler_Transmit_Buffer[0], src, &my_address, + &npdu_data); + if (service_data->segmented_message) { + /* we don't support segmentation - send an abort */ + len = + abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, ABORT_REASON_SEGMENTATION_NOT_SUPPORTED, + true); +#if PRINT_ENABLED + fprintf(stderr, "Alarm Ack: Segmented message. Sending Abort!\n"); +#endif + goto AA_ABORT; + } + + len = alarm_ack_decode_service_request(service_request, service_len, &data); +#if PRINT_ENABLED + if (len <= 0) + fprintf(stderr, "Alarm Ack: Unable to decode Request!\n"); +#endif + if (len < 0) { + /* bad decoding - send an abort */ + len = + abort_encode_apdu(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, ABORT_REASON_OTHER, true); +#if PRINT_ENABLED + fprintf(stderr, "Alarm Ack: Bad Encoding. Sending Abort!\n"); +#endif + goto AA_ABORT; + } + + /* + ** Process Life Safety Operation Here + */ +#if PRINT_ENABLED + fprintf(stderr, + "Alarm Ack Operation: Received acknowledge for object id %d from %s for process id %d for object %id\n", + data.eventObjectIdentifier.instance, + data.ackSource.value, + data.ackProcessIdentifier, + data.eventObjectIdentifier.instance); +#endif + + len = + encode_simple_ack(&Handler_Transmit_Buffer[pdu_len], + service_data->invoke_id, SERVICE_CONFIRMED_ACKNOWLEDGE_ALARM); +#if PRINT_ENABLED + fprintf(stderr, "Alarm Acknowledge: " "Sending Simple Ack!\n"); +#endif + + AA_ABORT: + pdu_len += len; + bytes_sent = + datalink_send_pdu(src, &npdu_data, &Handler_Transmit_Buffer[0], + pdu_len); +#if PRINT_ENABLED + if (bytes_sent <= 0) + fprintf(stderr, "Alarm Acknowledge: " "Failed to send PDU (%s)!\n", + strerror(errno)); +#endif + + return; +} diff --git a/bacnet-stack/demo/handler/h_lso.c b/bacnet-stack/demo/handler/h_lso.c index 17a810ca..632e1cdb 100644 --- a/bacnet-stack/demo/handler/h_lso.c +++ b/bacnet-stack/demo/handler/h_lso.c @@ -37,7 +37,7 @@ #include "lso.h" #include "handlers.h" -bool handler_lso( +void handler_lso( uint8_t * service_request, uint16_t service_len, BACNET_ADDRESS * src, diff --git a/bacnet-stack/demo/handler/s_ack_alarm.c b/bacnet-stack/demo/handler/s_ack_alarm.c new file mode 100644 index 00000000..588652a4 --- /dev/null +++ b/bacnet-stack/demo/handler/s_ack_alarm.c @@ -0,0 +1,112 @@ +/************************************************************************** +* +* Copyright (C) 2009 John Minack +* +* Permission is hereby granted, free of charge, to any person obtaining +* a copy of this software and associated documentation files (the +* "Software"), to deal in the Software without restriction, including +* without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to +* permit persons to whom the Software is furnished to do so, subject to +* the following conditions: +* +* The above copyright notice and this permission notice shall be included +* in all copies or substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY +* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, +* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE +* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +* +*********************************************************************/ +#include +#include +#include +#include +#include "config.h" +#include "config.h" +#include "txbuf.h" +#include "bacdef.h" +#include "bacdcode.h" +#include "address.h" +#include "tsm.h" +#include "npdu.h" +#include "apdu.h" +#include "device.h" +#include "datalink.h" +#include "dcc.h" +#include "whois.h" +/* some demo stuff needed */ +#include "handlers.h" +#include "txbuf.h" +#include "alarm_ack.h" + +/* returns the invoke ID for confirmed request, or zero on failure */ + + +uint8_t Send_Alarm_Acknowledgement( + uint32_t device_id, + BACNET_ALARM_ACK_DATA *data) +{ + BACNET_ADDRESS dest; + BACNET_ADDRESS my_address; + unsigned max_apdu = 0; + uint8_t invoke_id = 0; + bool status = false; + int len = 0; + int pdu_len = 0; + int bytes_sent = 0; + BACNET_NPDU_DATA npdu_data; + + 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) + invoke_id = tsm_next_free_invokeID(); + if (invoke_id) { + /* encode the NPDU portion of the packet */ + datalink_get_my_address(&my_address); + npdu_encode_npdu_data(&npdu_data, true, MESSAGE_PRIORITY_NORMAL); + pdu_len = + npdu_encode_pdu(&Handler_Transmit_Buffer[0], &dest, &my_address, + &npdu_data); + len = + alarm_ack_encode_apdu(&Handler_Transmit_Buffer[pdu_len], invoke_id, + data); + pdu_len += len; + /* 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, + &npdu_data, &Handler_Transmit_Buffer[0], (uint16_t) pdu_len); + bytes_sent = + datalink_send_pdu(&dest, &npdu_data, + &Handler_Transmit_Buffer[0], pdu_len); +#if PRINT_ENABLED + if (bytes_sent <= 0) + fprintf(stderr, "Failed to Send Alarm Ack Request (%s)!\n", + strerror(errno)); +#endif + } else { + tsm_free_invoke_id(invoke_id); + invoke_id = 0; +#if PRINT_ENABLED + fprintf(stderr, + "Failed to Send Alarm Ack Request " + "(exceeds destination maximum APDU)!\n"); +#endif + } + } + + return invoke_id; +} + diff --git a/bacnet-stack/demo/handler/s_lso.c b/bacnet-stack/demo/handler/s_lso.c new file mode 100644 index 00000000..dd77d6db --- /dev/null +++ b/bacnet-stack/demo/handler/s_lso.c @@ -0,0 +1,112 @@ +/************************************************************************** +* +* Copyright (C) 2009 John Minack +* +* Permission is hereby granted, free of charge, to any person obtaining +* a copy of this software and associated documentation files (the +* "Software"), to deal in the Software without restriction, including +* without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to +* permit persons to whom the Software is furnished to do so, subject to +* the following conditions: +* +* The above copyright notice and this permission notice shall be included +* in all copies or substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY +* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, +* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE +* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +* +*********************************************************************/ +#include +#include +#include +#include +#include "config.h" +#include "config.h" +#include "txbuf.h" +#include "bacdef.h" +#include "bacdcode.h" +#include "address.h" +#include "tsm.h" +#include "npdu.h" +#include "apdu.h" +#include "device.h" +#include "datalink.h" +#include "dcc.h" +#include "whois.h" +/* some demo stuff needed */ +#include "handlers.h" +#include "txbuf.h" +#include "lso.h" + +/* returns the invoke ID for confirmed request, or zero on failure */ + + +uint8_t Send_Life_Safety_Operation_Data( + uint32_t device_id, + BACNET_LSO_DATA *data) +{ + BACNET_ADDRESS dest; + BACNET_ADDRESS my_address; + unsigned max_apdu = 0; + uint8_t invoke_id = 0; + bool status = false; + int len = 0; + int pdu_len = 0; + int bytes_sent = 0; + BACNET_NPDU_DATA npdu_data; + + 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) + invoke_id = tsm_next_free_invokeID(); + if (invoke_id) { + /* encode the NPDU portion of the packet */ + datalink_get_my_address(&my_address); + npdu_encode_npdu_data(&npdu_data, true, MESSAGE_PRIORITY_NORMAL); + pdu_len = + npdu_encode_pdu(&Handler_Transmit_Buffer[0], &dest, &my_address, + &npdu_data); + len = + lso_encode_adpu(&Handler_Transmit_Buffer[pdu_len], invoke_id, + data); + pdu_len += len; + /* 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, + &npdu_data, &Handler_Transmit_Buffer[0], (uint16_t) pdu_len); + bytes_sent = + datalink_send_pdu(&dest, &npdu_data, + &Handler_Transmit_Buffer[0], pdu_len); +#if PRINT_ENABLED + if (bytes_sent <= 0) + fprintf(stderr, "Failed to Send Life Safe Op Request (%s)!\n", + strerror(errno)); +#endif + } else { + tsm_free_invoke_id(invoke_id); + invoke_id = 0; +#if PRINT_ENABLED + fprintf(stderr, + "Failed to Send Life Safe Op Request " + "(exceeds destination maximum APDU)!\n"); +#endif + } + } + + return invoke_id; +} + diff --git a/bacnet-stack/include/alarm_ack.h b/bacnet-stack/include/alarm_ack.h new file mode 100644 index 00000000..78fe0505 --- /dev/null +++ b/bacnet-stack/include/alarm_ack.h @@ -0,0 +1,92 @@ +/*####COPYRIGHTBEGIN#### + ------------------------------------------- + Copyright (C) 2009 John Minack + + This program is free software; you can redistribute it and/or + modify it under the terms of the GNU General Public License + as published by the Free Software Foundation; either version 2 + of the License, or (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to: + The Free Software Foundation, Inc. + 59 Temple Place - Suite 330 + Boston, MA 02111-1307, USA. + + As a special exception, if other files instantiate templates or + use macros or inline functions from this file, or you compile + this file and link it with other works to produce a work based + on this file, this file does not by itself cause the resulting + work to be covered by the GNU General Public License. However + the source code for this file must still be made available in + accordance with section (3) of the GNU General Public License. + + This exception does not invalidate any other reasons why a work + based on this file might be covered by the GNU General Public + License. + ------------------------------------------- +####COPYRIGHTEND####*/ + +#ifndef ALARM_ACK_H_ +#define ALARM_ACK_H_ + +#include "bacenum.h" +#include +#include +#include "bacapp.h" +#include "timestamp.h" + +typedef struct { + uint32_t ackProcessIdentifier; + BACNET_OBJECT_ID eventObjectIdentifier; + BACNET_EVENT_TYPE eventTypeAcked; + BACNET_TIMESTAMP eventTimeStamp; + BACNET_CHARACTER_STRING ackSource; + BACNET_TIMESTAMP ackTimeStamp; +} BACNET_ALARM_ACK_DATA; + +#ifdef __cplusplus +extern "C" { +#endif /* __cplusplus */ + +/*************************************************** +** +** Creates a Alarm Acknowledge APDU +** +****************************************************/ + int alarm_ack_encode_apdu( + uint8_t * apdu, + uint8_t invoke_id, + BACNET_ALARM_ACK_DATA * data); + +/*************************************************** +** +** Encodes the service data part of Alarm Acknowledge +** +****************************************************/ + int alarm_ack_encode_service_request( + uint8_t * apdu, + BACNET_ALARM_ACK_DATA * data); + +/*************************************************** +** +** Decodes the service data part of Alarm Acknowledge +** +****************************************************/ + int alarm_ack_decode_service_request( + uint8_t * apdu, + unsigned apdu_len, + BACNET_ALARM_ACK_DATA * data); + +#ifdef __cplusplus +} +#endif /* __cplusplus */ +#endif /* ALARM_ACK_H_ */ + + + diff --git a/bacnet-stack/include/client.h b/bacnet-stack/include/client.h index 4da021cf..28b62670 100644 --- a/bacnet-stack/include/client.h +++ b/bacnet-stack/include/client.h @@ -36,7 +36,8 @@ #include "rpm.h" #include "cov.h" #include "event.h" - +#include "lso.h" +#include "alarm_ack.h" #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ @@ -149,6 +150,12 @@ extern "C" { void Send_Initialize_Routing_Table_Ack( BACNET_ROUTER_PORT * router_port_list); + uint8_t Send_Life_Safety_Operation_Data( + uint32_t device_id, + BACNET_LSO_DATA *data); + uint8_t Send_Alarm_Acknowledgement( + uint32_t device_id, + BACNET_ALARM_ACK_DATA *data); diff --git a/bacnet-stack/include/handlers.h b/bacnet-stack/include/handlers.h index 4bb1f2cc..8f731b79 100644 --- a/bacnet-stack/include/handlers.h +++ b/bacnet-stack/include/handlers.h @@ -170,12 +170,18 @@ extern "C" { uint16_t service_len, BACNET_ADDRESS * src); - bool handler_lso( + void handler_lso( uint8_t * service_request, uint16_t service_len, BACNET_ADDRESS * src, BACNET_CONFIRMED_SERVICE_DATA * service_data); + void handler_alarm_ack( + uint8_t * service_request, + uint16_t service_len, + BACNET_ADDRESS * src, + BACNET_CONFIRMED_SERVICE_DATA * service_data); + #ifdef __cplusplus } diff --git a/bacnet-stack/src/alarm_ack.c b/bacnet-stack/src/alarm_ack.c new file mode 100644 index 00000000..115f0a32 --- /dev/null +++ b/bacnet-stack/src/alarm_ack.c @@ -0,0 +1,233 @@ +/*####COPYRIGHTBEGIN#### + ------------------------------------------- + Copyright (C) 2009 John Minack + + This program is free software; you can redistribute it and/or + modify it under the terms of the GNU General Public License + as published by the Free Software Foundation; either version 2 + of the License, or (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to: + The Free Software Foundation, Inc. + 59 Temple Place - Suite 330 + Boston, MA 02111-1307, USA. + + As a special exception, if other files instantiate templates or + use macros or inline functions from this file, or you compile + this file and link it with other works to produce a work based + on this file, this file does not by itself cause the resulting + work to be covered by the GNU General Public License. However + the source code for this file must still be made available in + accordance with section (3) of the GNU General Public License. + + This exception does not invalidate any other reasons why a work + based on this file might be covered by the GNU General Public + License. + ------------------------------------------- +####COPYRIGHTEND####*/ + +#include "alarm_ack.h" + +/*************************************************** +** +** Creates an Unconfirmed Event Notification APDU +** +****************************************************/ +int alarm_ack_encode_apdu( + uint8_t * apdu, + uint8_t invoke_id, + BACNET_ALARM_ACK_DATA * data) +{ + int len = 0; /* length of each encoding */ + int apdu_len = 0; /* total length of the apdu, return value */ + + if (apdu) { + apdu[0] = PDU_TYPE_CONFIRMED_SERVICE_REQUEST; + apdu[1] = encode_max_segs_max_apdu(0, MAX_APDU); + apdu[2] = invoke_id; + apdu[3] = SERVICE_CONFIRMED_ACKNOWLEDGE_ALARM; /* service choice */ + apdu_len = 4; + + len = alarm_ack_encode_service_request(&apdu[apdu_len], data); + apdu_len += len; + } + + return apdu_len; +} + + +/*************************************************** +** +** Encodes the service data part of Event Notification +** +****************************************************/ +int alarm_ack_encode_service_request( + uint8_t * apdu, + BACNET_ALARM_ACK_DATA * data) +{ + int len = 0; /* length of each encoding */ + int apdu_len = 0; /* total length of the apdu, return value */ + + if (apdu) { + len = encode_context_unsigned(&apdu[apdu_len], 0, data->ackProcessIdentifier); + apdu_len += len; + + len = encode_context_object_id(&apdu[apdu_len], 1, data->eventObjectIdentifier.type, data->eventObjectIdentifier.instance); + apdu_len += len; + + len = encode_context_enumerated(&apdu[apdu_len], 2, data->eventTypeAcked); + apdu_len += len; + + len = bacapp_encode_context_timestamp(&apdu[apdu_len], 3, &data->eventTimeStamp); + apdu_len += len; + + len = encode_context_character_string(&apdu[apdu_len], 4, &data->ackSource); + apdu_len += len; + + len = bacapp_encode_context_timestamp(&apdu[apdu_len], 5, &data->ackTimeStamp); + apdu_len += len; + } + + return apdu_len; +} + + +/*************************************************** +** +** Decodes the service data part of Event Notification +** +****************************************************/ +int alarm_ack_decode_service_request( + uint8_t * apdu, + unsigned apdu_len, + BACNET_ALARM_ACK_DATA * data) +{ + int len = 0; + int section_len; + + if (-1 == (section_len = + decode_context_unsigned(&apdu[len], 0, &data->ackProcessIdentifier))) { + return -1; + } + len += section_len; + + if (-1 == (section_len = + decode_context_object_id(&apdu[len], 1, &data->eventObjectIdentifier.type, &data->eventObjectIdentifier.instance))) { + return -1; + } + len += section_len; + + if (-1 == (section_len = + decode_context_enumerated(&apdu[len], 2, (int*)&data->eventTypeAcked))) { + return -1; + } + len += section_len; + + if (-1 == (section_len = + bacapp_decode_context_timestamp(&apdu[len], 3, &data->eventTimeStamp))) { + return -1; + } + len += section_len; + + if (-1 == (section_len = + decode_context_character_string(&apdu[len], 4, &data->ackSource))) { + return -1; + } + len += section_len; + + if (-1 == (section_len = + bacapp_decode_context_timestamp(&apdu[len], 5, &data->ackTimeStamp))) { + return -1; + } + len += section_len; + + return len; +} + +#ifdef TEST + +#include +#include +#include "ctest.h" + + +void testAlarmAck( + Test * pTest) +{ + BACNET_ALARM_ACK_DATA testAlarmAckIn; + BACNET_ALARM_ACK_DATA testAlarmAckOut; + + uint8_t buffer[MAX_APDU]; + int inLen; + int outLen; + + testAlarmAckIn.ackProcessIdentifier = 0x1234; + characterstring_init_ansi(&testAlarmAckIn.ackSource, "This is a test"); + testAlarmAckIn.ackTimeStamp.tag = TIME_STAMP_SEQUENCE; + testAlarmAckIn.ackTimeStamp.value.sequenceNum = 0x4331; + testAlarmAckIn.eventObjectIdentifier.instance = 567; + testAlarmAckIn.eventObjectIdentifier.type = OBJECT_DEVICE; + testAlarmAckIn.eventTimeStamp.tag = TIME_STAMP_TIME; + testAlarmAckIn.eventTimeStamp.value.time.hour = 10; + testAlarmAckIn.eventTimeStamp.value.time.min = 11; + testAlarmAckIn.eventTimeStamp.value.time.sec = 12; + testAlarmAckIn.eventTimeStamp.value.time.hundredths = 14; + testAlarmAckIn.eventTypeAcked = EVENT_CHANGE_OF_LIFE_SAFETY; + + memset(&testAlarmAckOut, 0, sizeof(testAlarmAckOut)); + + + inLen = alarm_ack_encode_service_request(buffer, &testAlarmAckIn); + outLen = alarm_ack_decode_service_request(buffer, inLen, &testAlarmAckOut); + + ct_test(pTest, inLen == outLen); + + ct_test(pTest, testAlarmAckIn.ackProcessIdentifier == testAlarmAckOut.ackProcessIdentifier); + + ct_test(pTest, testAlarmAckIn.ackTimeStamp.tag == testAlarmAckOut.ackTimeStamp.tag); + ct_test(pTest, testAlarmAckIn.ackTimeStamp.value.sequenceNum == testAlarmAckOut.ackTimeStamp.value.sequenceNum); + + ct_test(pTest, testAlarmAckIn.ackProcessIdentifier == testAlarmAckOut.ackProcessIdentifier); + + ct_test(pTest, testAlarmAckIn.eventObjectIdentifier.instance == testAlarmAckOut.eventObjectIdentifier.instance); + ct_test(pTest, testAlarmAckIn.eventObjectIdentifier.type == testAlarmAckOut.eventObjectIdentifier.type); + + ct_test(pTest, testAlarmAckIn.eventTimeStamp.tag == testAlarmAckOut.eventTimeStamp.tag); + ct_test(pTest, testAlarmAckIn.eventTimeStamp.value.time.hour == testAlarmAckOut.eventTimeStamp.value.time.hour); + ct_test(pTest, testAlarmAckIn.eventTimeStamp.value.time.min == testAlarmAckOut.eventTimeStamp.value.time.min); + ct_test(pTest, testAlarmAckIn.eventTimeStamp.value.time.sec == testAlarmAckOut.eventTimeStamp.value.time.sec); + ct_test(pTest, testAlarmAckIn.eventTimeStamp.value.time.hundredths == testAlarmAckOut.eventTimeStamp.value.time.hundredths); + + ct_test(pTest, testAlarmAckIn.eventTypeAcked == testAlarmAckOut.eventTypeAcked); + +} + + +#ifdef TEST_ALARM_ACK +int main( + void) +{ + Test *pTest; + bool rc; + + pTest = ct_create("BACnet Alarm Ack", NULL); + /* individual tests */ + rc = ct_addTestFunction(pTest, testAlarmAck); + assert(rc); + + ct_setStream(pTest, stdout); + ct_run(pTest); + (void) ct_report(pTest); + ct_destroy(pTest); + + return 0; +} + +#endif /* TEST_ALARM_ACK */ +#endif /* TEST */