⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 homesensorcoord.c

📁 Micro controladores jennic wireless networking zigbee
💻 C
📖 第 1 页 / 共 5 页
字号:
        || (u16NodeAddr >= (DEMO_ENDPOINT_ADDR_BASE + DEMO_ENDPOINTS)))
    {
        return;
    }

    /* Store data for node */
    u8Node = (uint8)(u16NodeAddr - DEMO_ENDPOINT_ADDR_BASE);
    psNodeData = &sDemoData.sNode.asNodeData[u8Node];

    psNodeData->u8FramesMissed = 0;
    psNodeData->u8SwitchOn = psFrame->au8Sdu[2];
    vLedControl(u8Node, psNodeData->u8SwitchOn);

    for (u8Count = 0; u8Count < DEMO_SENSOR_LIST_LEN; u8Count++)
    {
        psNodeData->asNodeElementData[u8Count].u8NowValue = psFrame->au8Sdu[u8Count + 3];
    }

    psNodeData->u8Rssi = psFrame->u8LinkQuality;
}

/****************************************************************************
 *
 * NAME: vProcessIncomingMlme
 *
 * DESCRIPTION:
 * Deals with any incoming MCPS events. If the event is an indication that
 * device wants to associate, goes through a process to determine a short
 * address for the device, either as 'next on the list' or the same address
 * that was proviously given if the device has associated before. Then sends
 * an association response via the stack.
 *
 * For debug purposes, also displays any Communication Status indications.
 *
 * PARAMETERS: Name        RW  Usage
 *             psMlmeInd   R   Pointer to structure containing MLME event
 *
 * RETURNS:
 * void
 *
 ****************************************************************************/
PRIVATE void vProcessIncomingMlme(MAC_MlmeDcfmInd_s *psMlmeInd)
{
    MAC_MlmeReqRsp_s   sMlmeReqRsp;
    MAC_MlmeSyncCfm_s  sMlmeSyncCfm;
    uint16             u16ShortAddress;
    uint8              u8Node;
    uint8              u8AssocStatus;

    switch (psMlmeInd->u8Type)
    {
    case MAC_MLME_IND_ASSOCIATE:
        /* Only respond if in network or node modes. We aren't a coordinator
           until then */
        if ((sDemoData.sSystem.eState == E_STATE_NETWORK)
            || (sDemoData.sSystem.eState == E_STATE_NODE)
            || (sDemoData.sSystem.eState == E_STATE_NODE_CONTROL))
        {
            /* Default short address */
            u16ShortAddress = 0xffff;

            /* Check node extended address matches and device wants short address
               (for the demo, we only use short address) */
            if (psMlmeInd->uParam.sIndAssociate.u8Capability & 0x80)
            {
                /* Check if already associated (idiot proofing) */
                u8Node = 0;
                while (u8Node < sDemoData.sNode.u8AssociatedNodes)
                {
                    if ((psMlmeInd->uParam.sIndAssociate.sDeviceAddr.u32L == sDemoData.sNode.asAssocNodes[u8Node].sExtAddr.u32L) &&
                        (psMlmeInd->uParam.sIndAssociate.sDeviceAddr.u32H == sDemoData.sNode.asAssocNodes[u8Node].sExtAddr.u32H))
                    {
                        /* Already in system: give it same short address */
                        u16ShortAddress = sDemoData.sNode.asAssocNodes[u8Node].u16ShortAddr;
                    }
                    u8Node++;
                }

                /* Assume association succeeded */
                u8AssocStatus = 0;

                if (u16ShortAddress == 0xffff)
                {
                    if (sDemoData.sNode.u8AssociatedNodes < DEMO_ENDPOINTS)
                    {
                        /* Allocate short address as next in list */
                        u16ShortAddress = DEMO_ENDPOINT_ADDR_BASE + sDemoData.sNode.u8AssociatedNodes;

                        /* Store details for future use */
                        sDemoData.sNode.asAssocNodes[sDemoData.sNode.u8AssociatedNodes].sExtAddr = psMlmeInd->uParam.sIndAssociate.sDeviceAddr;
                        sDemoData.sNode.asAssocNodes[sDemoData.sNode.u8AssociatedNodes].u16ShortAddr = u16ShortAddress;
                        sDemoData.sNode.u8AssociatedNodes++;
                    }
                    else
                    {
                        /* PAN access denied */
                        u8AssocStatus = 2;
                    }
                }

                /* Update display if necessary */
                if (sDemoData.sSystem.eState == E_STATE_NETWORK)
                {
                    vBuildNetworkScreen(sDemoData.sGui.eCurrentSensor);
                }
            }
            else
            {
                /* PAN access denied */
                u8AssocStatus = 2;
            }

            /* Create association response */
            sMlmeReqRsp.u8Type = MAC_MLME_RSP_ASSOCIATE;
            sMlmeReqRsp.u8ParamLength = sizeof(MAC_MlmeRspAssociate_s);
            sMlmeReqRsp.uParam.sRspAssociate.sDeviceAddr = psMlmeInd->uParam.sIndAssociate.sDeviceAddr;
            sMlmeReqRsp.uParam.sRspAssociate.u16AssocShortAddr = u16ShortAddress;
            sMlmeReqRsp.uParam.sRspAssociate.u8Status = u8AssocStatus;
            sMlmeReqRsp.uParam.sRspAssociate.u8SecurityEnable = FALSE;

            /* Send association response */
            vAppApiMlmeRequest(&sMlmeReqRsp, &sMlmeSyncCfm);

            /* There is no confirmation for an association response, hence no need to check */
        }
        break;
    }
}

/****************************************************************************
 *
 * NAME: bProcessForTimeout
 *
 * DESCRIPTION:
 * Processes any incoming hardware events to see if the event is wake-up
 * timer 0 firing, as this is the only hardware event responded to.
 *
 * PARAMETERS: Name          RW Usage
 *             psHardwareInd R  Pointer to structure containing hardware event
 *
 * RETURNS:
 * TRUE if event was wake-up timer 0 firing.
 *
 ****************************************************************************/
PRIVATE bool_t bProcessForTimeout(AppQApiHwInd_s *psHardwareInd)
{
    /* Check to see if hardware indication was for wake timer 0 */
    if ((psHardwareInd->u32DeviceId == E_AHI_DEVICE_SYSCTRL)
        && (psHardwareInd->u32ItemBitmap & (1 << E_AHI_SYSCTRL_WK0)))
    {
        return TRUE;
    }

    return FALSE;
}

/****************************************************************************
 *
 * NAME: vProcessUpdateBlock
 *
 * DESCRIPTION:
 * Called once per second to update the scrolling graphs and, if showing a
 * screen with graphs on, updating the LCD.
 *
 * RETURNS:
 * void
 *
 ****************************************************************************/
PRIVATE void vProcessUpdateBlock(void)
{
    tsNodeData *psNodeData;
    tsNodeElementData *psNodeElementData;
    uint8 *pu8GraphData;
    uint8 u8PrevPoint;
    uint8 u8Node;
    uint8 u8Sensor;
    uint8 u8Value;

    /* Update graphs */
    for (u8Node = 0; u8Node < DEMO_ENDPOINTS; u8Node++)
    {
        psNodeData = &sDemoData.sNode.asNodeData[u8Node];
        if (psNodeData->u8FramesMissed)
        {
            /* Missed data, so copy previous value forward */
            u8PrevPoint = (sDemoData.sGui.u8GraphPos - 1) & (DEMO_HISTORY_LEN - 1);
            for (u8Sensor = 0; u8Sensor < DEMO_SENSOR_LIST_LEN; u8Sensor++)
            {
                pu8GraphData = psNodeData->asNodeElementData[u8Sensor].au8GraphData;
                pu8GraphData[sDemoData.sGui.u8GraphPos] = pu8GraphData[u8PrevPoint];
            }
        }
        else
        {
            /* Data must be scaled for graph (0-13)
               Temp range is 0-52
               Humidity range is 0-104
               Light range is 0-6
            */
            for (u8Sensor = 0; u8Sensor < DEMO_SENSOR_LIST_LEN; u8Sensor++)
            {
                psNodeElementData = &psNodeData->asNodeElementData[u8Sensor];
                u8Value = psNodeElementData->u8NowValue;
                switch (u8Sensor)
                {
                case E_SENSOR_TEMP:
                    u8Value = u8Value >> 2;
                    break;

                case E_SENSOR_HTS:
                    u8Value = u8Value >> 3;
                    break;

                case E_SENSOR_ALS:
                    u8Value = u8Value * 2;
                    break;
                }
                if (u8Value > 13)
                {
                    u8Value = 13;
                }
                psNodeElementData->au8GraphData[sDemoData.sGui.u8GraphPos] = u8Value;
            }
        }

        /* For next time, assume failed until proven otherwise */
        if (psNodeData->u8FramesMissed < FRAMES_MISSED_INDICATION)
        {
            psNodeData->u8FramesMissed++;
        }
    }

    /* Increment graph position */
    sDemoData.sGui.u8GraphPos = (sDemoData.sGui.u8GraphPos + 1) & (DEMO_HISTORY_LEN - 1);

    /* Update display */
    switch (sDemoData.sSystem.eState)
    {
    case E_STATE_NETWORK:
        vUpdateNetworkScreen(sDemoData.sGui.eCurrentSensor);
        break;

    case E_STATE_NODE:
        vUpdateNodeScreen(sDemoData.sGui.u8CurrentNode);
        break;

    default:
        break;
    }
}

/****************************************************************************
 *
 * NAME: vProcessSetChannelKeyPress
 *
 * DESCRIPTION:
 * Handles button presses on the Set Channel screen. There is one parameter
 * that can be adjusted (the channel) and buttons to navigate to two other
 * screens.
 *
 * PARAMETERS:      Name        RW  Usage
 *                  u8KeyMap    R   Current buttons pressed bitmap
 *
 * RETURNS:
 * void
 *
 ****************************************************************************/
PRIVATE void vProcessSetChannelKeyPress(uint8 u8KeyMap)
{
    switch (u8KeyMap)
    {
    case E_KEY_0:
        /* Further setup button: go to setup screen */
        sDemoData.sSystem.eState = E_STATE_SETUP_SCREEN;
        vBuildSetupScreen();
        break;

    case E_KEY_1:
        /* Plus button: increment value */
    case E_KEY_2:
        /* Minus button: decrement value */

        vAdjustAlarm(&sDemoData.sSystem.u8Channel, CHANNEL_MAX, CHANNEL_MIN, u8KeyMap == E_KEY_1);
        vUpdateSetChannelScreen();
        break;

    case E_KEY_3:
        /* Done button: start beaconing and go to network screen */
        vStartBeacon();
        sDemoData.sSystem.eState = E_STATE_NETWORK;
        vBuildNetworkScreen(sDemoData.sGui.eCurrentSensor);
        break;

    default:
        break;
    }
}

/****************************************************************************
 *
 * NAME: vProcessNetworkKeyPress
 *
 * DESCRIPTION:
 * Handles button presses on the Network screen. The buttons can move onto
 * the first Node screen (if there are any nodes) or select a particular
 * sensor.
 *
 * PARAMETERS:      Name        RW  Usage
 *                  u8KeyMap    R   Current buttons pressed bitmap
 *
 * RETURNS:
 * void
 *
 ****************************************************************************/
PRIVATE void vProcessNetworkKeyPress(uint8 u8KeyMap)
{
    switch (u8KeyMap)
    {
    case E_KEY_0:
        /* Node button: go to node screen (if there are any nodes) */
        if (sDemoData.sNode.u8AssociatedNodes > 0)
        {
            sDemoData.sSystem.eState = E_STATE_NODE;
            sDemoData.sGui.u8CurrentNode = 0;
            vBuildNodeScreen(sDemoData.sGui.u8CurrentNode);
        }
        break;

    case E_KEY_1:
        /* Temp button: change if not already there */
        vUpdateNetworkSensor(E_SENSOR_TEMP);
        break;

    case E_KEY_2:
        /* Humidity button: change if not already there */
        vUpdateNetworkSensor(E_SENSOR_HTS);
        break;

    case E_KEY_3:
        /* Temp button: change if not already there */
        vUpdateNetworkSensor(E_SENSOR_ALS);
        break;
    }
}

/****************************************************************************
 *
 * NAME: vUpdateNetworkSensor
 *
 * DESCRIPTION:
 * Simple function to save a little code. If the user presses a button on the
 * Network screen to select a sensor, this checks that the sensor is not the
 * same as the current sensor before updating the screen.
 *
 * PARAMETERS:      Name            RW  Usage
 *                  eSensor         R   New sensor to display
 *
 * RETURNS:
 * void
 *
 ****************************************************************************/
PRIVATE void vUpdateNetworkSensor(teSensor eSensor)
{
    if (sDemoData.sGui.eCurrentSensor != eSensor)
    {
        sDemoData.sGui.eCurrentSensor = eSensor;
        vBuildNetworkScreen(eSensor);
    }
}
/****************************************************************************
 *
 * NAME: vProcessNodeKeyPress
 *
 * DESCRIPTION:
 * Handles button presses on the Node screens. The first button can move to
 * the next Node screen (if there are any more nodes) or back to the Network
 * screen. Another button selects the Node Control screen and the other two
 * toggle the state of the remote switch.
 *
 * PARAMETERS:      Name        RW  Usage
 *                  u8KeyMap    R   Current buttons pressed bitmap
 *
 * RETURNS:
 * void
 *
 ****************************************************************************/
PRIVATE void vProcessNodeKeyPress(uint8 u8KeyMap)
{
    switch (u8KeyMap)
    {
    case E_KEY_0:
        /* Node button: go to next node or network screen */
        sDemoData.sGui.u8CurrentNode++;
        if (sDemoData.sGui.u8CurrentNode == sDemoData.sNode.u8AssociatedNodes)
        {
            sDemoData.sSystem.eState = E_STATE_NETWORK;
            sDemoData.sGui.eCurrentSensor = E_SENSOR_TEMP;
            vBuildNetworkScreen(E_SENSOR_TEMP);
        }
        else
        {
            vBuildNodeScreen(sDemoData.sGui.u8CurrentNode);
        }
        break;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -