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

📄 demozrfdapp.c

📁 zbee potocol 無線通訊測試.平台:microchip 18f452 與 cc2420 zbee 晶片.含coord端與rfd端
💻 C
📖 第 1 页 / 共 3 页
字号:
            if ( APLIsRejoinComplete() )
            {
                // If there was no error, continue with normal logic.
                // Or else handle as per application requirements.
                if ( GetLastZError() == ZCODE_NO_ERROR )
                {
                    ConsolePutROMString(rejoinSuccessMsg);
                    LEDBindingTask();

                    smApp = SM_APP_NORMAL_RUN;
                }
                // else there was an error and needs to be addressed.
                else
                {
                    ConsolePutROMString(rejoinFailedMsg);


                    // This action would depend on application.

                    // For time-being, we will simply keep trying to rejoin.
                    smApp = SM_APP_NORMAL_START;
                }
            }
            break;

        case SM_APP_NORMAL_RUN:
	        LED_ReceiveTask();
	        LED_SendTask();
            // In this demo, we will wakeup if someone pushed a button
            /*if ( appFlags.bits.S2Toggled )
            {
                appFlags.bits.S2Toggled = FALSE;
                smApp = SM_APP_RUN_S2_TASK;
            }

            // or watchdog timer expired and we need to update D1.
            else
                smApp = SM_APP_RUN_D1_TASK;*/

            break;

        case SM_APP_RUN_S2_TASK:
            // Once switch is toggled, we run the task until it is complete
            // and go back to sleep.
           
            if ( S2Task() )
            {
                // Once we update the S2 value, check for binding action
                smApp = SM_APP_SLEEP;

                GIEL = 0;
            }
            break;

        case SM_APP_RUN_D1_TASK:
            // After watchdog has expired, run the lamp task until it is complete.	
            if ( D1Task() )
                smApp = SM_APP_SLEEP;
            break;

        case SM_APP_SLEEP:
            
            if ( appFlags.bits.S2Toggled )
                smApp = SM_APP_NORMAL_RUN;

            // Before going to sleep, make sure that all outgoing transmissions are
            // complete
            else if ( APLIsIdle() )
            {
                DEBUG_OUT("Going to sleep...\r\n");

                // Since some of the logic might have transmitted something on USART
                // make sure that it is completely transmitted before we put core to sleep
                // or else the outgoing UART data will be corrupted.
                while ( !ConsoleIsPutReady() );

                // Disable the stack.
                APLDisable();

                // The TMR0 will stop counting while sleeping, so
                // turn off D2 to make sure power isn't wasted.
                D2 = 0;

                // Make sure that we wakeup from key press.
                RBIE = 1;

                SLEEP();

                NOP();


                DEBUG_OUT("Just woke-up from sleep...\r\n");

                GIEL = 1;


                // Reenable the stack.
                APLEnable();

                smApp = SM_APP_NORMAL_RUN;
            }

           break;
        }
    }
}



static BOOL IsMACAddrAssigned(void)
{
    // Read MAC long address from app-specific nonvolatile memory.
    NVMRead(&macInfo.longAddr,
                 (ROM void*)&macLongAddr,
                 sizeof(macInfo.longAddr));

    // An address is said to be invlaid if its OUI matches with our preset OUI
    if ( macInfo.longAddr.v[7] != MAC_LONG_ADDR_BYTE7 ||
         macInfo.longAddr.v[6] != MAC_LONG_ADDR_BYTE6 ||
         macInfo.longAddr.v[5] != MAC_LONG_ADDR_BYTE5 )
         return FALSE;

    else
        return TRUE;
}


// 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.
    if ( !appFlags.bits.bInConfigMode )
        D2 = 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.
    if ( !appFlags.bits.bInConfigMode )
        D2 = 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;
}




static void InitializeBoard(void)
{
    // This is a RS232 console - you may replace it with any console you like.
    ConsoleInit();

    // Switches S2 and S3 are on RB5 and RB4 respectively. We want interrupt-on-change
    INTCON = 0x00;

    // There is no external pull-up resistors on S2 and S3. We will use internal pull-ups.
    // The CC2420 provides SFD (Start of Frame Detect) signal on RB2. We are using
    // the falling edge of that signal to generate INT2
    // Enable PORTB internal pullups, INT2 on falling edge
    INTCON2 = 0x00;

    // Enable INT2 interrupt - SFD from CC2420
    INTCON3 = 0xD0;

    // CC2420 I/O assignments with respect to PIC:
    // RB0 <- FIFO      (Input)
    // RB1 <- CCA       (Input - Not used in this version of stack)
    // RB2 <- SFD       (Input - Generates interrupt on falling edge)
    // RB3 <- FIFOP     (Input - Used to detect overflow)
    // RC0 -> CSn       (Output - to select CC2420 SPI slave)
    // RC1 -> VREG_EN   (Output - to enable CC2420 voltage regulator)
    // RC2 -> RESETn    (Output - to reset CC2420)
    // RC3 - > SCK      (Output - SPI Clock to CC2420)
    // RC4 <- SO        (Input - SPI data from CC2420)
    // RC5 -> SI        (Output - SPI data to CC2420)

    // Make PORTB as input - this is the RESET default
    TRISB = 0xff;

    // Set PORTC control signal direction and initial states
    // Start with CC2420 disabled and not selected
    LATC = 0xfd;

    // Set the SPI module for use by Stack
    TRISC = 0xD0;

    // Set the SPI module
    SSPSTAT = 0xC0;
    SSPCON1 = 0x20;


    // D1 and D2 are on RA0 and RA1 respectively, and CS of TC77 is on RA2.
    // Make PORTA as digital I/O.
    // The TC77 temp sensor CS is on RA2.
    ADCON1 = 0x0F;

    // Deselect TC77 (RA2)
    LATA = 0x04;

    // Make RA0, RA1, RA2 and RA4 as outputs.
    TRISA = 0xE0;


    // Enable global interrupts.
    GIEL = 1;
    GIEH = 1;
}


// 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
#if defined(MCHP_C18)
    #pragma interruptlow HighISR
    void HighISR(void)
#elif defined(HITECH_C18)
    void interrupt HighISR(void)
#else
    void HighISR(void)
#endif
{
    // This is a quick way to display MAC TX/RX status on RD1 LED.
    // TMR0IF is also used by TickUpdate, so we will let it clear the flag.
    if ( !appFlags.bits.bInConfigMode )
    {
       if ( TMR0IF )
            D2 = 0;
    }

    // Must call this so that MAC module can determine if a transmission is progress or not.
    MACISR();

    // Must call this so that tick manager can update its tick count.
    TickUpdate();

    // Is this a interrupt-on-change interrupt?
    if ( RBIF == 1 )
    {
        // Clear mismatch condition and flag
        if ( S2 == 0 )
            appFlags.bits.S2Toggled = TRUE;

        // Disable further RBIF until we process it
        RBIE = 0;

        // Clear mis-match condition
        LATB = PORTB;

        RBIF = 0;

    }
}

#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



/*
 * ConfigTask is a blocking task that is executed when micro is reset with S3 pushed down.
 * To indicate that config mode is entered, RD0 LED is turned ON.
 *
 * Once in config mode, you would see config menu on RS232 terminal. Use 19200, 8-N-1.
 * When micro is first programmed, you must set its node id. Without valid node id,
 * board will automatically enter into config mode. Once a node id is set, board will
 * only enter into config mode if S3 was pushed down on startup.
 *
 */
static void ConfigTask(void)
{
    MENU_CMD c;

    ConsolePutROMString(menu);

    // While in config mode, disable PORTB interrupt-on-change.
    RBIE = 0;

    // Turn D1 & D2 ON to indicate that we are in config mode.
    D1 = 1;
    D2 = 1;

    // Wait for S3 to get released
    while( S3 == 0 );

    while( 1 )
    {
        // Check to see if there was any key press in terminal.
        if ( ConsoleIsGetReady() )
        {
            // Get the key value.
            c = ConsoleGet();

            // If this is a valid command, execute it.
            if ( ExecuteMenuChoice(c) )
                // After completion of every menu command or invalid command
                // redisplay the menu message.
                ConsolePutROMString(menu);

            else // Quit command is executed
            {
                // Display message and quit
                ConsolePutROMString(exitMsg);
                break;
            }
        }

        // If S2 alone is pressed in config mode, do join.
        else if ( S2 == 0 && S3 == 1 )
            ExecuteMenuChoice(MENU_CMD_JOIN);

        else if ( S2 == 0 && S3 == 0 )
            BindingTask();

    }

    // Turn OFF D1 & D2 to indicate that we are leaving config mode.
    D1 = 0;
    D2 = 0;
}

static void LEDBindingTask(void)
{
    enum { LED_S_BINDING_IDLE, LED_S_BINDING_WAIT, LED_D_BINDING_IDLE, LED_D_BINDING_WAIT } ledBinding;

    ledBinding = LED_S_BINDING_IDLE;

    while(1)
    {
        APLTask();

        switch(ledBinding)
        {
        case LED_S_BINDING_IDLE:
            
            // Show that we are about to bind LED EP.
            ConsolePutROMString(LEDSrcBindingMsg);

            StartLEDCustomBind(CUSTOM_BIND_SOURCE, EP_LED_S);

            // Now wait for respone from coordinator
            ledBinding = LED_S_BINDING_WAIT;

            // Enable Watchdog to catch lock-ups.
            ENABLE_WDT();

            break;

        case LED_S_BINDING_WAIT:
            CLRWDT();

            if ( IsLEDBindComplete() )
            {
                ConsolePutROMString(ledSrcBindCompleteMsg);

                // Disable watchdog before returning.
                DISABLE_WDT();
		ledBinding = LED_D_BINDING_IDLE;
                //return;
                
            }
        
            break;
        case LED_D_BINDING_IDLE:
            
            // Show that we are about to bind LED EP.
            ConsolePutROMString(LEDDecBindingMsg);

            StartLEDCustomBind(CUSTOM_BIND_DEST, EP_LED_D);

            // Now wait for respone from coordinator
            ledBinding = LED_D_BINDING_WAIT;

            // Enable Watchdog to catch lock-ups.
            ENABLE_WDT();

            break;

        case LED_D_BINDING_WAIT:
            CLRWDT();

            if ( IsLEDBindComplete() )
            {
                ConsolePutROMString(ledSrcBindCompleteMsg);

                // Disable watchdog before returning.
                DISABLE_WDT();

                return;
            }
            break;
        }
    }
}

static void BindingTask(void)
{
    enum { SM_BINDING_IDLE, SM_BINDING_WAIT } smBinding;

    smBinding = SM_BINDING_IDLE;

    while(1)
    {
        // Keep the stack going...
        APLTask();

        switch(smBinding)
        {
        case SM_BINDING_IDLE:
            // Binding action starts when both S2 and S3 are pressed.
            {
                // Indicate that we are entering into binding task.
                D1 = 1;
                D2 = 1;

                // Wait until one of the swithes is released.

⌨️ 快捷键说明

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