From caaf9befefc34e68e3c424c0f179863cdb1ab97d Mon Sep 17 00:00:00 2001 From: skarg Date: Mon, 6 Feb 2006 16:54:21 +0000 Subject: [PATCH] Added demo handler for ReinitializeDevice service, and included it in the demo/server. Tested using Synergy Lighting panel client on the serial console. --- bacnet-stack/demo/handler/h_rd.c | 136 ++++++++++++++++++++++++++ bacnet-stack/demo/handler/handlers.h | 5 + bacnet-stack/demo/server/Makefile | 2 + bacnet-stack/demo/server/makefile.b32 | 2 + bacnet-stack/demo/server/server.c | 3 + 5 files changed, 148 insertions(+) create mode 100644 bacnet-stack/demo/handler/h_rd.c diff --git a/bacnet-stack/demo/handler/h_rd.c b/bacnet-stack/demo/handler/h_rd.c new file mode 100644 index 00000000..d2d14f72 --- /dev/null +++ b/bacnet-stack/demo/handler/h_rd.c @@ -0,0 +1,136 @@ +/************************************************************************** +* +* Copyright (C) 2006 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 "bacerror.h" +#include "apdu.h" +#include "npdu.h" +#include "abort.h" +#include "reject.h" +#include "rd.h" + +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) +{ + 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 */ + } + 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)); + + return; +} diff --git a/bacnet-stack/demo/handler/handlers.h b/bacnet-stack/demo/handler/handlers.h index e9852b92..b4a89cc5 100644 --- a/bacnet-stack/demo/handler/handlers.h +++ b/bacnet-stack/demo/handler/handlers.h @@ -90,6 +90,11 @@ void handler_atomic_read_file_ack( 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); #ifdef __cplusplus } diff --git a/bacnet-stack/demo/server/Makefile b/bacnet-stack/demo/server/Makefile index 6c3ef3fb..e99e6770 100644 --- a/bacnet-stack/demo/server/Makefile +++ b/bacnet-stack/demo/server/Makefile @@ -29,6 +29,7 @@ SRCS = server.c \ $(BACNET_HANDLER)/h_rp.c \ $(BACNET_HANDLER)/h_wp.c \ $(BACNET_HANDLER)/h_arf.c \ + $(BACNET_HANDLER)/h_rd.c \ $(BACNET_OBJECT)/device.c \ $(BACNET_OBJECT)/ai.c \ $(BACNET_OBJECT)/ao.c \ @@ -47,6 +48,7 @@ SRCS = server.c \ $(BACNET_ROOT)/rp.c \ $(BACNET_ROOT)/wp.c \ $(BACNET_ROOT)/arf.c \ + $(BACNET_ROOT)/rd.c \ $(BACNET_ROOT)/abort.c \ $(BACNET_ROOT)/reject.c \ $(BACNET_ROOT)/bacerror.c \ diff --git a/bacnet-stack/demo/server/makefile.b32 b/bacnet-stack/demo/server/makefile.b32 index 20a6b982..afa0c1bc 100644 --- a/bacnet-stack/demo/server/makefile.b32 +++ b/bacnet-stack/demo/server/makefile.b32 @@ -28,6 +28,7 @@ SRCS = server.c \ ..\..\demo\handler\h_rp.c \ ..\..\demo\handler\h_wp.c \ ..\..\demo\handler\h_arf.c \ + ..\..\demo\handler\h_rd.c \ ..\..\bacdcode.c \ ..\..\bacapp.c \ ..\..\bacstr.c \ @@ -40,6 +41,7 @@ SRCS = server.c \ ..\..\wp.c \ ..\..\arf.c \ ..\..\awf.c \ + ..\..\rd.c \ ..\..\demo\object\bacfile.c \ ..\..\demo\object\device.c \ ..\..\demo\object\ai.c \ diff --git a/bacnet-stack/demo/server/server.c b/bacnet-stack/demo/server/server.c index a264727b..20acb5e1 100644 --- a/bacnet-stack/demo/server/server.c +++ b/bacnet-stack/demo/server/server.c @@ -71,6 +71,9 @@ static void Init_Service_Handlers(void) apdu_set_confirmed_handler( SERVICE_CONFIRMED_ATOMIC_READ_FILE, handler_atomic_read_file); + apdu_set_confirmed_handler( + SERVICE_CONFIRMED_REINITIALIZE_DEVICE, + handler_reinitialize_device); } static void cleanup(void)