pingpong.c

Back to Ping-Pong sample application.

00001 
00017 #include <configServer.h>    // Config Server header
00018 #include <taskManager.h>
00019 #include <appFramework.h>    // Main stack types
00020 #include <appTimer.h>        // Application timer header
00021 #include <apsMacros.h>
00022 #include <pingpong.h>        // Own application header
00023 #include <uart.h>
00024 #include <uid.h>
00025 #include <aps.h>             // Main APS header
00026 #include <zdo.h>             // Main ZDO header
00027 
00028 #ifdef _DBG_
00029   #include <dbgPort.h>
00030 #endif // _DBG_
00031 
00032 
00033 /***********************************************************************************
00034   Local variables
00035 ***********************************************************************************/
00036 
00037 static DeviceType_t appDeviceType = 0;  // Device type (Router/Coordinator/End device)
00038 static uint8_t dataPayload; // Payload
00039 static uint8_t appPayload[APP_PAYLOAD_SIZE + APS_AFFIX_LENGTH]; // Buffer for application payload
00040 bool fwPacketFlag = false;  // Flag indicating that device is currently forwarding a packet
00041 
00042 static AppState_t appState = APP_INITING_STATE; // Current application state
00043 static ZDO_StartNetworkReq_t networkParams; // Request params for ZDO_StartNetworkReq
00044 
00045 #ifdef TEST_NETWORK
00046 static HAL_UartDescriptor_t appUartDescriptor; // UART descriptor (required by stack)
00047 #endif // TEST_NETWORK
00048 
00049 // Endpoint parameters
00050 static SimpleDescriptor_t simpleDescriptor = {END_POINT, 1, 1, 1, 0, 0 , NULL, 0, NULL};
00051 static APS_RegisterEndpointReq_t endpointParams;
00052 
00053 static HAL_AppTimer_t startingNetworkTimer; // Timer indicating starting network
00054 static HAL_AppTimer_t delayFwTimer;         // Timer period of waiting before forwarding packet to next node
00055 
00056 static APS_DataReq_t dataReq;        // Request for APS_DataReq primitive
00057 
00058 static ShortAddr_t srcAddr;          // Own network address
00059 static ShortAddr_t dstAddr;          // Destination network address
00060 
00061 /***********************************************************************************
00062   Local functions
00063 ***********************************************************************************/
00064 
00065 static void ZDO_StartNetworkConf(ZDO_StartNetworkConf_t *confirmInfo); // Network start/join confirmation
00066 static void APS_DataInd(APS_DataInd_t *indData); // Data reception handler
00067 static void APS_DataConf(APS_DataConf_t *confInfo);  // Data transmission confirmation handler
00068 static void buttonReleased(uint8_t buttonNumber); // Button release event handler
00069 static void prepareMsgParams(void); // Configures general data message parameters
00070 
00071 #ifdef TEST_NETWORK
00072 // UART related functions (only required for test network)
00073 static void uartInit(void);
00074 static void uartSendHeartbeat(void);
00075 static void uartWriteConf(void);
00076 #endif // TEST_NETWORK
00077 
00078 /********************************************************************
00079   Description: Starting network timer has fired. Toggle LED for blink
00080 
00081   Parameters: none.
00082 
00083   Returns: nothing.
00084 ********************************************************************/
00085 void startingNetworkTimerFired(void)
00086 {
00087   appToggleLed(NETWORK_LED);
00088 }
00089 
00090 /********************************************************************
00091   Description: Packet forwarding delay has expired. Forward packet and turn indicating LED off
00092 
00093   Parameters: none.
00094 
00095   Returns: nothing.
00096 ********************************************************************/
00097 void delayFwTimerFired(void)
00098 {
00099   appOnLed(DATA_LED);
00100   APS_DataReq(&dataReq);
00101 }
00102 
00103 /********************************************************************
00104   Description: Application task handler
00105 
00106   Parameters: none.
00107 
00108   Returns: nothing.
00109 ********************************************************************/
00110 void APL_TaskHandler(void)
00111 {
00112   switch (appState)
00113   {
00114     // Node is in initial state
00115     case APP_INITING_STATE:
00116     {
00117       uint64_t extPanId = COORDINATOR_EXT_PANID;
00118       CS_WriteParameter(CS_EXT_PANID_ID, &extPanId);
00119 
00120 #ifdef _DBG_
00121       configure_dbgu();
00122 #endif // _DBG_
00123 
00124       endpointParams.simpleDescriptor = &simpleDescriptor;
00125 
00126       // Read switches and assign own network address
00127        //uint8_t dswitch = 0;
00128       uint8_t dswitch;
00129       dswitch = appReadSliders() & 7;
00130 
00131       srcAddr = dswitch & 3;
00132 
00133       // If 3rd switch is on then destination address is 0 (coordinator)
00134       if (dswitch & 4)
00135         dstAddr = 0;
00136       else
00137         dstAddr = srcAddr + 1;
00138 
00139       CS_WriteParameter(CS_NWK_ADDR_ID, &srcAddr); // Assign own NWK address
00140       // Set device type: logical address equal to 0 is coordinator, otherwise router
00141       appDeviceType = srcAddr ? DEVICE_TYPE_ROUTER : DEVICE_TYPE_COORDINATOR;
00142       CS_WriteParameter(CS_DEVICE_TYPE_ID, &appDeviceType);
00143 
00144 #ifdef _SECURITY_
00145       if (DEVICE_TYPE_COORDINATOR == appDeviceType)
00146       {
00147         CS_WriteParameter(CS_UID_ID, &extPanId);
00148         CS_WriteParameter(CS_APS_TRUST_CENTER_ADDRESS_ID, &extPanId);
00149       }
00150 #endif
00151 
00152 #ifdef TEST_NETWORK
00153       if (DEVICE_TYPE_COORDINATOR == appDeviceType)
00154         uartInit();
00155 #endif // TEST_NETWORK
00156 
00157       { // Use static network addressing
00158         bool useStatAddr = true;
00159         CS_WriteParameter(CS_NWK_UNIQUE_ADDR_ID, &useStatAddr);
00160       }
00161 
00162       { // Set transceiver to be always on (no sleeping)
00163         bool rxOnWhenIdleFlag = true;
00164         CS_WriteParameter(CS_RX_ON_WHEN_IDLE_ID, &rxOnWhenIdleFlag);
00165       }
00166 
00167       appOpenLeds();
00168 
00169       endpointParams.APS_DataInd = APS_DataInd;   // Register handler for incoming data packets
00170       appState = APP_AWAITING_NETWORK_START_STATE; // Switch to awaiting network start state
00171       SYS_PostTask (APL_TASK_ID);
00172       break;
00173     }
00174 
00175     // Node is waiting network start/join request
00176     case APP_AWAITING_NETWORK_START_STATE:
00177       appOpenButtons(NULL, buttonReleased); // Set handlers for button events
00178 
00179 #ifndef _BUTTONS_ // Button press simulating.
00180       buttonReleased(NETWORK_BUTTON);
00181 #endif // _BUTTONS_
00182       break;
00183 
00184     // Node is starting/joining network
00185     case APP_NETWORK_STARTING_STATE:
00186       {
00187         uint32_t chMask = CS_CHANNEL_MASK;
00188 
00189         // Set network request parameters
00190         CS_WriteParameter(CS_CHANNEL_MASK_ID, &chMask);
00191         networkParams.ZDO_StartNetworkConf = ZDO_StartNetworkConf; // Handler for network start confirmation
00192         ZDO_StartNetworkReq(&networkParams); // Start/join network
00193       }
00194       break;
00195 
00196       // Data sending after indication
00197     case APP_NETWORK_DATA_SENDING_STATE:
00198       // No packet is being currently forwarded by the device
00199       if (fwPacketFlag == false)
00200       {
00201         // Set payload value
00202         appPayload[APS_ASDU_OFFSET] = dataPayload;
00203         dataReq.asdu = (uint8_t *) &appPayload[APS_ASDU_OFFSET];
00204         // Start delay packet transmission timer
00205         delayFwTimer.interval = TIMER_FW_DELAY;
00206         delayFwTimer.mode     = TIMER_ONE_SHOT_MODE;
00207         delayFwTimer.callback = delayFwTimerFired;
00208 
00209         HAL_StartAppTimer(&delayFwTimer);
00210         appState = APP_WAITING_CONFIRM_STATE; // Switch application state
00211         fwPacketFlag = true; // Mark node as currently forwarding a packet
00212       }
00213       else
00214       {
00215         SYS_PostTask(APL_TASK_ID);
00216       }
00217       break;
00218 
00219       // Waiting confirm
00220     case APP_WAITING_CONFIRM_STATE:
00221       break;
00222 
00223     // Node is in network
00224     case APP_IN_NETWORK_STATE:
00225 #ifndef _BUTTONS_
00226   #if FINAL_DEVICE
00227         buttonReleased(DATA_TX_BUTTON); // Button released event simulating.
00228   #endif // FINAL_DEVICE == 1
00229 #endif // _BUTTONS_
00230       break;
00231 
00232     // Node is out of network
00233     case APP_NO_NETWORK_STATE:
00234       break;
00235 
00236     default:
00237       break;
00238   }
00239 }
00240 
00241 /********************************************************************
00242   Description: ZDO_StartNetwork primitive confirmation was received.
00243 
00244   Parameters: confirmInfo - confirmation information
00245 
00246   Returns: nothing.
00247 ********************************************************************/
00248 void ZDO_StartNetworkConf(ZDO_StartNetworkConf_t *confirmInfo)
00249 {
00250   // Network start/join was successful
00251   if (ZDO_SUCCESS_STATUS == confirmInfo->status)
00252   {
00253     HAL_StopAppTimer(&startingNetworkTimer); // Stop network led blinking
00254     appOnLed(NETWORK_LED); // Indicate successfull network start/join
00255 
00256     CS_WriteParameter(CS_STACK_PROFILE_ID, &endpointParams.simpleDescriptor->AppProfileId);
00257 
00258     APS_RegisterEndpointReq(&endpointParams); // Register endpoint
00259     prepareMsgParams(); // Set basic data message parameters
00260 
00261     appState = APP_IN_NETWORK_STATE; // Switch application state
00262   }
00263 
00264   SYS_PostTask(APL_TASK_ID);
00265 }
00266 
00267 /********************************************************************
00268   Description: Button release handler
00269 
00270   Parameters: buttonNumber - number of button being released
00271 
00272   Returns: nothing.
00273 ********************************************************************/
00274 static void buttonReleased(uint8_t buttonNumber)
00275 {
00276   // Start/join network request
00277   if ((APP_AWAITING_NETWORK_START_STATE == appState) && (NETWORK_BUTTON == buttonNumber))
00278   {
00279     // Set and start timer for LED blinking during network start
00280     startingNetworkTimer.interval = TIMER_STARTING_NETWORK;
00281     startingNetworkTimer.mode     = TIMER_REPEAT_MODE;
00282     startingNetworkTimer.callback = startingNetworkTimerFired;
00283     HAL_StartAppTimer(&startingNetworkTimer);
00284 
00285     appState = APP_NETWORK_STARTING_STATE; // Switch application state
00286     SYS_PostTask(APL_TASK_ID);
00287   }
00288 
00289   // Initialize data packet transmission
00290   else if ((DATA_TX_BUTTON == buttonNumber) &&
00291            (APP_IN_NETWORK_STATE == appState) &&
00292            (false == fwPacketFlag))
00293   {
00294     uint8_t data = 0; // Initial payload value
00295     fwPacketFlag = true; // Transmitting packet, disable packet forwarding
00296 
00297     appPayload[APS_ASDU_OFFSET] = data;
00298     dataReq.asdu = (uint8_t *) &appPayload[APS_ASDU_OFFSET];
00299 
00300     // Configure and start delay packet forwarding timer
00301     delayFwTimer.interval = TIMER_FW_DELAY;
00302     delayFwTimer.mode     = TIMER_ONE_SHOT_MODE;
00303     delayFwTimer.callback = delayFwTimerFired;
00304     HAL_StartAppTimer(&delayFwTimer);
00305 
00306     appState = APP_WAITING_CONFIRM_STATE; // Switch application state
00307   }
00308 }
00309 
00310 /********************************************************************
00311   Description: Confirmation of message received.
00312   Turn off data forwarding indication LED
00313 
00314   Parameters: confData - confirmation information
00315 
00316   Returns: nothing.
00317 ********************************************************************/
00318 static void APS_DataConf(APS_DataConf_t *confData)
00319 {
00320   // TODO: add status checking
00321   confData = confData;         // Unused parameter, warning prevention
00322   fwPacketFlag = false;      // Enable packet forwarding
00323 
00324   if (APS_SUCCESS_STATUS != confData->status)
00325   {
00326     appState = APP_NETWORK_DATA_SENDING_STATE;
00327     SYS_PostTask(APL_TASK_ID);
00328   }
00329   else
00330   {
00331     appOffLed(DATA_LED);    // Transmission completed, turn off indication
00332 
00333     if (APP_WAITING_CONFIRM_STATE == appState)
00334       appState = APP_IN_NETWORK_STATE; // Switch application state
00335   }
00336 }
00337 
00338 /********************************************************************
00339   Description: Handler of aps data indication
00340 
00341   Parameters: indData - structure of incoming msg
00342 
00343   Returns: nothing.
00344 ********************************************************************/
00345 void APS_DataInd(APS_DataInd_t *indData)
00346 {
00347   // Update payload value
00348   dataPayload = *(indData->asdu);
00349 
00350   if (DEVICE_TYPE_ROUTER == appDeviceType)
00351   {
00352     dataPayload += 1;
00353     appState = APP_NETWORK_DATA_SENDING_STATE;
00354   }
00355   else
00356   {
00357     dataPayload = 0;
00358 #ifdef TEST_NETWORK
00359     appState = APP_SENDING_HEARTBEAT;
00360     uartSendHeartbeat();
00361 #else
00362     appState = APP_NETWORK_DATA_SENDING_STATE;
00363 #endif // TEST_NETWORK
00364   }
00365 
00366   SYS_PostTask(APL_TASK_ID);
00367 }
00368 
00369 /********************************************************************
00370   Description: Prepare common data request parameters
00371 
00372   Parameters: none.
00373 
00374   Returns: nothing.
00375 ********************************************************************/
00376 void prepareMsgParams(void)
00377 {
00378   dataReq.dstAddrMode             = APS_SHORT_ADDRESS; // Use short (NWK) addressing
00379   dataReq.dstAddress.shortAddress = dstAddr;       // Destination NWK address
00380   dataReq.dstEndpoint             = END_POINT;       // Destination endpoint
00381   dataReq.profileId               = endpointParams.simpleDescriptor->AppProfileId;
00382   dataReq.clusterId               = 1;
00383   dataReq.srcEndpoint             = END_POINT;
00384   dataReq.asduLength              = APP_PAYLOAD_SIZE;
00385   dataReq.txOptions.acknowledgedTransmission = 1;//APP_USE_APS_ACK; // Whether ACKs on application level are used
00386   dataReq.radius                  = 0;
00387   dataReq.APS_DataConf            = APS_DataConf;  // Confirm callback function
00388 }
00389 
00390 /********************************************************************
00391   Description: update network status event handler
00392 
00393   Parameters: nwkParams - new network parameters
00394 
00395   Returns: nothing.
00396 ********************************************************************/
00397 void ZDO_MgmtNwkUpdateNotf(ZDO_MgmtNwkUpdateNotf_t *nwkParams)
00398 {
00399   // Network is lost/left
00400   if (ZDO_NETWORK_LOST_STATUS == nwkParams->status)
00401   {
00402     HAL_StartAppTimer(&startingNetworkTimer); // Start indication of network join process
00403     appState = APP_NETWORK_STARTING_STATE;    // Switch application state
00404 
00405     SYS_PostTask(APL_TASK_ID);
00406   }
00407 }
00408 
00409 /********************************************************************
00410   Description: dummy wakeup event handler
00411 
00412   Parameters: none.
00413 
00414   Returns: nothing.
00415 ********************************************************************/
00416 void ZDO_WakeUpInd(void)
00417 {
00418 }
00419 
00420 /********************************************************************
00421   Description: dummy sleep event handler
00422 
00423   Parameters: none.
00424 
00425   Returns: nothing.
00426 ********************************************************************/
00427 void ZDO_SleepInd(void)
00428 {
00429 }
00430 
00431 #ifdef TEST_NETWORK
00432 /********************************************************************
00433   Description: Init UART, register UART callbacks.
00434 
00435   Parameters: none.
00436 
00437   Returns: nothing.
00438 ********************************************************************/
00439 static void uartInit(void)
00440 {
00441   appUartDescriptor.tty             = APP_UART_CHANNEL;
00442   appUartDescriptor.mode            = ASYNC;
00443   appUartDescriptor.baudrate        = UART_BAUDRATE_38400;
00444   appUartDescriptor.dataLength      = UART_DATA8;
00445   appUartDescriptor.parity          = UART_PARITY_NONE;
00446   appUartDescriptor.stopbits        = UART_STOPBIT_1;
00447   appUartDescriptor.rxBuffer        = NULL;
00448   appUartDescriptor.rxBufferLength  = 0;
00449   appUartDescriptor.txBuffer        = NULL;
00450   appUartDescriptor.txBufferLength  = 0;
00451   appUartDescriptor.rxCallback      = NULL;
00452   appUartDescriptor.txCallback      = uartWriteConf;
00453   appUartDescriptor.flowControl     = UART_FLOW_CONTROL_NONE;
00454 
00455   HAL_OpenUart(&appUartDescriptor);
00456 }
00457 
00458 /********************************************************************
00459   Description: Send Heartbeat Signal To Uart
00460 
00461   Parameters: none
00462 
00463   Returns: nothing.
00464 ********************************************************************/
00465 static void uartSendHeartbeat(void)
00466 {
00467   static uint8_t heartbeat = '#';
00468 
00469   HAL_WriteUart(&appUartDescriptor, &heartbeat, 1);
00470 }
00471 
00472 /********************************************************************
00473   Description: Writing confirmation has been received.
00474 
00475   Parameters: none.
00476 
00477   Returns: nothing.
00478 ********************************************************************/
00479 static void uartWriteConf(void)
00480 {
00481   appState = APP_NETWORK_DATA_SENDING_STATE;
00482 }
00483 #endif // TEST_NETWORK
00484 
00485 //eof pingpong.c

Generated on Tue Feb 17 16:44:56 2009 for BitCloud Stack Documentation by  doxygen 1.5.1-p1