📄 hcswitchc.c
字号:
{
DEBUG_OUT( "Giving up on waiting for switch acknowledge.\r\n" );
// We are done processing a switch press.
smSwitch = SM_SWITCH_INIT;
return TRUE;
}
else
{
smSwitch = SM_SWITCH_UPDATE;
DEBUG_OUT( "Timeout waiting for switch acknowledge. Trying again...\r\n" );
}
}
break;
#ifdef GET_APS_ACK
case SM_SWITCH_APS_WAIT:
if ( APLIsAPSConfirmed( OnOffSRC_CLUSTER ) )
{
// We have an APS acknowledge for our message, so we know the
// lamp endpoint has received the message. Reset the state
// machine for the next button press.
DEBUG_OUT( "Switch APS acknowledge received.\r\n" );
APLRemoveAPSACK();
#ifdef GET_AF_RESPONSE
// Set the state machine to get the application framework
// response.
smSwitch = SM_SWITCH_AF_WAIT;
#else
// We are done processing a switch press.
smSwitch = SM_SWITCH_INIT;
return TRUE;
#endif
}
else if (TickGetDiff(TickGet(), messageTimeSent) >= RESPONSE_WAIT_DURATION)
{
DEBUG_OUT( "Timeout waiting for APS-level ACK.\r\n" );
smSwitch = SM_SWITCH_INIT;
return TRUE;
}
break;
#endif
#ifdef GET_AF_RESPONSE
case SM_SWITCH_AF_WAIT:
if (APLIsGetReady())
{
dataTypeAndCommand = APLGet(); // This is really the sequence number.
dataTypeAndCommand = APLGet();
attribID.byte.LSB = APLGet();
attribID.byte.MSB = APLGet();
errorCode = APLGet();
if ((dataTypeAndCommand & TRANS_COMMAND_TYPE_MASK) != TRANS_SET_RESP)
{
DEBUG_OUT( "Invalid AF response.\r\n" );
}
else if (attribID.Val != OnOffSRC_OnOff)
{
DEBUG_OUT( "Invalid Attribute ID in response.\r\n" );
}
else if (errorCode != KVP_SUCCESS)
{
DEBUG_OUT( "Error response received from light.\r\n" );
}
else
{
DEBUG_OUT( "Received AF response.\r\n" );
}
smSwitch = SM_SWITCH_INIT;
return TRUE;
}
else if (TickGetDiff(TickGet(), messageTimeSent) >= RESPONSE_WAIT_DURATION)
{
DEBUG_OUT( "Timeout waiting for AF-level response.\r\n" );
smSwitch = SM_SWITCH_INIT;
return TRUE;
}
break;
#endif
}
// We still have more to do with processing the switch press.
return FALSE;
}
//******************************************************************************
// Interrupt Service Routine
//******************************************************************************
// NOTE: Several PICs, including the PIC18F4620 revision A3 have a RETFIE FAST/MOVFF bug
// The interruptlow keyword is used to work around the bug when using C18.
// To work around the bug on PICC-18, configure the compiler to Compile for ICD
// We buffer the received packet in the interrupt handler, which requires 16-bit
// and 32-bit math. Therefore, we must save the temporary registers, the math
// data section, and the PROD register.
#if defined(MCHP_C18)
#pragma interruptlow HighISR save=section(".tmpdata"),section("MATH_DATA"),PROD
void HighISR(void)
#elif defined(HITECH_C18)
void interrupt HighISR(void)
#else
void HighISR(void)
#endif
{
if ( TMR0IF )
MESSAGE_INDICATION = 0;
// Must call this so that MAC module can determine if a transmission is
// in progress or not.
APL_ISR();
// Must call this so that tick manager can update its tick count.
// TMR0IF is also used by TickUpdate, so we will let it clear the flag.
TickUpdate();
// Is this a interrupt-on-change interrupt?
if ( RBIF == 1 )
{
// Record which button was pressed so the main() loop can
// handle it
if (BIND_SWITCH == 0)
appFlags.bits.bBindSwitchToggled = TRUE;
if (LIGHT_SWITCH == 0)
appFlags.bits.bLightSwitchToggled = TRUE;
// Disable further RBIF until we process it
RBIE = 0;
// Clear mis-match condition and reset the interrupt flag
LATB = PORTB;
RBIF = 0;
}
}
//******************************************************************************
// Interrupt Vectors
//******************************************************************************
#if defined(MCHP_C18)
#pragma code highVector=0x08
void HighVector (void)
{
_asm goto HighISR _endasm
}
#pragma code /* return to default code section */
#endif
#if defined(MCHP_C18)
#pragma code lowhVector=0x18
void LowVector (void)
{
_asm goto HighISR _endasm
}
#pragma code /* return to default code section */
#endif
/*********************************************************************
* Function: static void SendEndDeviceBindReq( void )
*
* PreCondition: Node is associated with a coordinator
*
* Input: None
*
* Output: None
*
* Side Effects: None
*
* Overview: Sends an end device bind request message to our
* ZDO. If possible, we will be bound to a
* complementary device.
*
* Note: Be sure to alloc the end device bind information.
* The ZDO will deallocate it for us.
********************************************************************/
static BOOL SendEndDeviceBindReq( void )
{
END_DEVICE_BIND_INFO *bindInfo;
if ((bindInfo = (END_DEVICE_BIND_INFO *)SRAMalloc( sizeof(END_DEVICE_BIND_INFO) )) == NULL)
return FALSE;
bindInfo->shortAddr = APLGetShortAddr;
bindInfo->EP = EP_SWITCH;
bindInfo->profileID = MY_PROFILE_ID;
bindInfo->numInClusters = 0;
bindInfo->inClusterList = NULL;
bindInfo->numOutClusters = 1;
if ((bindInfo->outClusterList = (BYTE *)SRAMalloc( 1 )) == NULL)
return FALSE;
bindInfo->outClusterList[0] = OnOffSRC_CLUSTER;
// Initialize the End Device Bind flags bResponseReceived and
// bBindSuccessful to FALSE. Clear these flags before calling
// Process_End_Device_Bind_req, because if we are the second one to
// request the bind, that function will set the appropriate flags.
endDeviceBindInfo.flags.Val = 0;
// Set our initial time so we can check for timeout.
endDeviceBindInfo.requestStart = TickGet();
Process_End_Device_Bind_req( bindInfo );
return TRUE;
}
//******************************************************************************
// Stack Callback Functions
//******************************************************************************
// Callback to process the End Device Bind response
void AppProcess_END_DEVICE_BIND_RSP( BOOL statusIsValid, BYTE status )
{
endDeviceBindInfo.flags.bits.bResponseReceived = 1;
if (!statusIsValid)
status = APLGet();
if (status == SUCCESS)
{
endDeviceBindInfo.flags.bits.bBindSuccessful = 1;
}
}
// Callback to application to notify of a frame transmission.
void AppMACFrameTransmitted(void)
{
// Turn on LED to indicate activity. TMR0IF interrupt will turn it off.
// See interrupt handler.
MESSAGE_INDICATION = 1;
}
// Callback to application to notify of a frame reception
void AppMACFrameReceived(void)
{
// Turn on LED to indicate activity. TMR0IF interrupt will turn it off.
// See interrupt handler.
MESSAGE_INDICATION = 1;
}
// Callback to application to notify of an ack timeout
void AppMACFrameTimeOutOccurred(void)
{
}
// Callback to an end device.
// Called when a suitable coordinator is found as part of associate process.
// Return TRUE if okay to associate.
// May use PANDesc.for more information about this coordinator.
// See MAC.h for definition of PANDesc.
BOOL AppOkayToAssociate(void)
{
return TRUE;
}
BOOL AppOkayToUseChannel(BYTE channel)
{
// This demo uses all available channels
// You may check given channel against your allowable channels and return TRUE
// or FALSE as needed.
// For 2.4GHz, channel = 11 through 26.
DEBUG_OUT("Now operating in next channel.\r\n");
return TRUE;
}
// Callback to application to notify if this node should be accepted to our network.
BOOL AppOkayToAcceptThisNode(LONG_ADDR *longAddr)
{
// In this demo, we would allow everyone to join our network.
// You may want to check the long address before allowing it.
#if 0
if(macInfo.longAddr.v[0]>0x7F)
{
if(longAddr->v[0]>0x7F)
{
return TRUE;
}
return FALSE;
}
else
{
if(longAddr->v[0]<=0x7F)
{
return TRUE;
}
return FALSE;
}
#endif
}
// Callback to application to noify of new node joining our network.
void AppNewNodeJoined(LONG_ADDR *nodeAddr, BOOL bIsRejoined)
{
// A new node has just joined (or rejoined).
// In this demo application, once a new node has joined, we want to save its
// association permanently into NVM.
if ( bIsRejoined == FALSE )
{
// You may want to check the nodeAddr and do something specific based
// on that node. This demo app does not any do anything special.
APLCommitTableChanges();
// Display that a new node has joined.
DEBUG_OUT( "A new node has joined.\r\n" );
}
else
{
// Display that a previous node has rejoined.
DEBUG_OUT( "A node has rejoined.\r\n" );
}
}
// Callback to application to notify that a node has left the network.
void AppNodeLeft(LONG_ADDR *nodeAddr)
{
// Display a message that a node has left the network.
DEBUG_OUT( "A node has left the network.\r\n" );
// Update our NVM table.
APLCommitTableChanges();
// Do application specific action here.
}
// Callback to application to notify that a route discovery attempt failed.
extern void AppRouteDiscoveryFailed( SHORT_ADDR shortAddr )
{
}
//******************************************************************************
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -