• CC2540 低功耗串口, POWER_SAVING 模式 下 串口 0 的使用


    低功耗 模式 下 使用 串口 ,  因为 PM2 或者 PM3 状态下  32M晶振 是不工作 的,根据手册得知没有32M晶振, 串口是不能工作的,但是可以使用 外部中断,因此,我把  串口的接收引脚设置为外部中断,这样 来唤醒BLE。

    这样就牵扯到 串口 和 外设中断  的 来回切换  ,具体操作方法如下:

    协议栈版本: ble_sdk_1.4.2.2   simpleBLEPeripheral

    1、   工程 配置 如下

    INT_HEAP_LEN=3072

    HALNODEBUG

    OSAL_CBTIMER_NUM_TASKS=1

    HAL_AES_DMA=TRUE

    HAL_DMA=TRUE

    POWER_SAVING

    xPLUS_BROADCASTER

    HAL_LCD=FALSE

    HAL_LED=TRUE

    HAL_KEY=FALSE

    HAL_UART=TRUE

    2、  在npi.h代码 中 做 如下修改

    #if !defined( NPI_UART_FC )

    #define NPI_UART_FC        FALSE//所长,2017年8月31日09:38:28,关闭流控

    #endif // !NPI_UART_FC

    3、  在_hal_uart_dma.c 文件 中 修改 DMA_PM 为0

    #if !defined( DMA_PM )

    #if defined POWER_SAVING

    #define DMA_PM                     0

    #else

    #define DMA_PM                     0

    #endif // POWER_SAVING

    #endif // !DMA_PM

    4、  ble休眠进入之前,使用串口的RX引脚外部中断来唤醒ble,配置如下:

      (我 放在 SimpleBLEPeripheral_Init 函数中,串口初始化函数后面)

    void initRxExterInterrupt(void)

    {

       P0SEL &= ~(0x08);      //P0.3 TX 设置为通用I/O口

       P0DIR &= ~(0x08);      //P0.3 TX 设置为输入

     

       P0SEL &= ~(0x04);      //P0.2 设置为通用I/O口

       P0DIR &= ~(0x04);      //P0.2 设置为输入

      

       P0IFG &= ~(0x04);      //P0.2 设置为输入

     

       PICTL |=  0;           //P0端口下降沿触发

       P0IEN |=  (0x04);       //P0.2 RX 中断使能

       IEN1  |=  0x20;        //端口P0中断使能

       EA = 1;                //开总中断

      

       U0CSR  &= ~0x40;     //关闭 串口 接收使能 

    }

    5、  在外部中断服务函数中,要 关闭RX 引脚的外部中断,函数如下:

    void initRxUart(void)

    {

       IEN1  &= ~0x20;     //端口P0中断关闭

       P0SEL |= (0x08);      //P0.3 TX 设置为外设串口TX功能

       P0DIR |= (0x08);      //P0.3 TX 设置为输出

    }

    6、  外部 中断服务函数如下

    #pragma vector = P0INT_VECTOR

    __interrupt void P0_ISR(void)

    {

      HAL_ENTER_ISR();

      if(0x04 & P0IFG) //判断 是否是 P0.2 RX 引脚 中断

      {

        initRxUart();

               //唤醒后 执行 定时任务 ,可以 这个任务中 使用 函数关闭 低功耗

        osal_start_timerEx( simpleBLEPeripheral_TaskID, SBP_PERIODIC_EVT, 5 );

        CLEAR_SLEEP_MODE();//退出 休眠 ,进入工作状态

        HAL_BOARD_INIT();//切换到外部32M 晶振 并且 等待稳定

      }

     

      P0IFG = 0; //清中断标志

      P0IF = 0; //清中断标志,IRCON[5],P0口中断

      HAL_EXIT_ISR();

    }

    7、  在 第六步 启动 的 定时任务中,static void performPeriodicTask( void )中

    使用 下面 两句代码  重新初始化串口,和关闭低功耗

        NPI_InitTransport(NpiSerialCallback);     //重新初始化串口

        osal_pwrmgr_device( PWRMGR_ALWAYS_ON ); // 不在进入低功耗

        printf(“Wakeup OK. ”);

    8、  重新进入低功耗 的 方法 :

    // makes sure LEDs are OFF

    HalLedSet( (HAL_LED_1 | HAL_LED_2), HAL_LED_MODE_OFF );

    HCI_EXT_ClkDivOnHaltCmd( HCI_EXT_ENABLE_CLK_DIVIDE_ON_HALT );

    HCI_EXT_HaltDuringRfCmd( HCI_EXT_HALT_DURING_RF_ENABLE );

    //关闭 定时事件,降低功耗

    osal_stop_timerEx( simpleBLEPeripheral_TaskID, SBP_PERIODIC_EVT );

    initRxExterInterrupt(); //重新 初始化 rx 为 外部中断

    osal_pwrmgr_device( PWRMGR_BATTERY );//打开 OSAL 进入低功耗的开关

    9、经过 测试 唤醒 过程需要  40mS 的时间。

      

    2017年8月31日11:11:26,所长,记录

  • 相关阅读:
    集合及特殊集合arrayList
    二维数组、多维数组
    一维数组

    for循坏的穷举与迭代,while、do while循环
    1.兔子生兔子问题2.打印菱形3.求100以内质数的和
    for循环嵌套
    复习题
    循环语句
    分支语句
  • 原文地址:https://www.cnblogs.com/suozhang/p/7457315.html
Copyright © 2020-2023  润新知