您当前的位置: 首页 > 

仙剑情缘

暂无认证

  • 4浏览

    0关注

    333博文

    0收益

  • 0浏览

    0点赞

    0打赏

    0留言

私信
关注
热门博文

NRF52832 PPI

仙剑情缘 发布时间:2018-10-31 17:54:49 ,浏览量:4

1.在sdk_config.h中加入宏

#ifndef PPI_ENABLED #define PPI_ENABLED 1 #endif

// TIMER_ENABLED - nrf_drv_timer - TIMER periperal driver - legacy layer //========================================================== #ifndef TIMER_ENABLED #define TIMER_ENABLED 1 #endif // TIMER_DEFAULT_CONFIG_FREQUENCY  - Timer frequency if in Timer mode   // 16 MHz  // 8 MHz  // 4 MHz  // 2 MHz  // 1 MHz  // 500 kHz  // 250 kHz  // 125 kHz  // 62.5 kHz  // 31.25 kHz 

#ifndef TIMER_DEFAULT_CONFIG_FREQUENCY #define TIMER_DEFAULT_CONFIG_FREQUENCY 4 #endif

// TIMER_DEFAULT_CONFIG_MODE  - Timer mode or operation   // Timer  // Counter 

#ifndef TIMER_DEFAULT_CONFIG_MODE #define TIMER_DEFAULT_CONFIG_MODE 0 #endif

// TIMER_DEFAULT_CONFIG_BIT_WIDTH  - Timer counter bit width   // 16 bit  // 8 bit  // 24 bit  // 32 bit 

#ifndef TIMER_DEFAULT_CONFIG_BIT_WIDTH #define TIMER_DEFAULT_CONFIG_BIT_WIDTH 3 #endif

// TIMER_DEFAULT_CONFIG_IRQ_PRIORITY  - Interrupt priority  

// Priorities 0,2 (nRF51) and 0,1,4,5 (nRF52) are reserved for SoftDevice // 0 (highest)  // 1  // 2  // 3  // 4  // 5  // 6  // 7 

#ifndef TIMER_DEFAULT_CONFIG_IRQ_PRIORITY #define TIMER_DEFAULT_CONFIG_IRQ_PRIORITY 6 #endif

#ifndef TIMER0_ENABLED #define TIMER0_ENABLED 1 #endif

// TIMER1_ENABLED  - Enable TIMER1 instance  

#ifndef TIMER1_ENABLED #define TIMER1_ENABLED 1 #endif

// TIMER2_ENABLED  - Enable TIMER2 instance  

#ifndef TIMER2_ENABLED #define TIMER2_ENABLED 1 #endif

// TIMER3_ENABLED  - Enable TIMER3 instance  

#ifndef TIMER3_ENABLED #define TIMER3_ENABLED 0 #endif

// TIMER4_ENABLED  - Enable TIMER4 instance  

#ifndef TIMER4_ENABLED #define TIMER4_ENABLED 0 #endif

2.导入nrfx_ppi.c,nrfx_timer.c,nrf_drv_ppi.c到工程 

3.定义时间间隔

#define PPI_EXAMPLE_TIMERS_PHASE_SHIFT_DELAY    (10)    // 1s = 10 * 100ms (Timer 0 interrupt) #define PPI_EXAMPLE_TIMER0_INTERVAL             (100)   // Timer interval in milliseconds #define PPI_EXAMPLE_TIMER1_INTERVAL             (2000)  // Timer interval in milliseconds #define PPI_EXAMPLE_TIMER2_INTERVAL             (2000)  // Timer interval in milliseconds 4.定义定时器实例 static const nrf_drv_timer_t m_timer0 = NRF_DRV_TIMER_INSTANCE(0); static const nrf_drv_timer_t m_timer1 = NRF_DRV_TIMER_INSTANCE(1); static const nrf_drv_timer_t m_timer2 = NRF_DRV_TIMER_INSTANCE(2); 5.定义变量

static nrf_ppi_channel_t m_ppi_channel1; static nrf_ppi_channel_t m_ppi_channel2;

static volatile uint32_t m_counter;

6.定义PPI事件处理函数

static void timer0_event_handler(nrf_timer_event_t event_type, void * p_context) {     ++m_counter; }

/* Timer event handler. Not used since Timer1 and Timer2 are used only for PPI. */ static void empty_timer_handler(nrf_timer_event_t event_type, void * p_context) { }

7.PPI初时化函数

/** @brief Function for initializing the PPI peripheral. */ static void ppi_init(void) {     uint32_t err_code = NRF_SUCCESS;

    err_code = nrf_drv_ppi_init();     APP_ERROR_CHECK(err_code);

    /* Configure 1st available PPI channel to stop TIMER0 counter on TIMER1 COMPARE[0] match,      * which is every even number of seconds.      */     err_code = nrf_drv_ppi_channel_alloc(&m_ppi_channel1);     APP_ERROR_CHECK(err_code);     err_code = nrf_drv_ppi_channel_assign(m_ppi_channel1,                                           nrf_drv_timer_event_address_get(&m_timer1,                                                                           NRF_TIMER_EVENT_COMPARE0),                                           nrf_drv_timer_task_address_get(&m_timer0,                                                                          NRF_TIMER_TASK_STOP));     APP_ERROR_CHECK(err_code);

    /* Configure 2nd available PPI channel to start TIMER0 counter at TIMER2 COMPARE[0] match,      * which is every odd number of seconds.      */     err_code = nrf_drv_ppi_channel_alloc(&m_ppi_channel2);     APP_ERROR_CHECK(err_code);     err_code = nrf_drv_ppi_channel_assign(m_ppi_channel2,                                           nrf_drv_timer_event_address_get(&m_timer2,                                                                           NRF_TIMER_EVENT_COMPARE0),                                           nrf_drv_timer_task_address_get(&m_timer0,                                                                          NRF_TIMER_TASK_START));     APP_ERROR_CHECK(err_code);

    // Enable both configured PPI channels     err_code = nrf_drv_ppi_channel_enable(m_ppi_channel1);     APP_ERROR_CHECK(err_code);     err_code = nrf_drv_ppi_channel_enable(m_ppi_channel2);     APP_ERROR_CHECK(err_code); } 8.定时器初时化

/** @brief Function for Timer 0 initialization.  *  @details Timer 0 will be stopped and started by Timer 1 and Timer 2 respectively using PPI.  *           It is configured to generate an interrupt every 100ms.  */ static void timer0_init(void) {     // Check TIMER0 configuration for details.     nrf_drv_timer_config_t timer_cfg = NRF_DRV_TIMER_DEFAULT_CONFIG;     timer_cfg.frequency = NRF_TIMER_FREQ_31250Hz;     ret_code_t err_code = nrf_drv_timer_init(&m_timer0, &timer_cfg, timer0_event_handler);     APP_ERROR_CHECK(err_code);

    nrf_drv_timer_extended_compare(&m_timer0,                                    NRF_TIMER_CC_CHANNEL0,                                    nrf_drv_timer_ms_to_ticks(&m_timer0,                                                              PPI_EXAMPLE_TIMER0_INTERVAL),                                    NRF_TIMER_SHORT_COMPARE0_CLEAR_MASK,                                    true); }

/** @brief Function for Timer 1 initialization.  *  @details Initializes TIMER1 peripheral to generate an event every 2 seconds. The events are  *           generated at even numbers of seconds after starting the example (2, 4, 6 ...) and they  *           are used to stop TIMER0 via PPI: TIMER1->EVENT_COMPARE[0] triggers TIMER0->TASK_STOP.  */ static void timer1_init(void) {     // Check TIMER1 configuration for details.     nrf_drv_timer_config_t timer_cfg = NRF_DRV_TIMER_DEFAULT_CONFIG;     timer_cfg.frequency = NRF_TIMER_FREQ_31250Hz;     ret_code_t err_code = nrf_drv_timer_init(&m_timer1, &timer_cfg, empty_timer_handler);     APP_ERROR_CHECK(err_code);

    nrf_drv_timer_extended_compare(&m_timer1,                                    NRF_TIMER_CC_CHANNEL0,                                    nrf_drv_timer_ms_to_ticks(&m_timer1,                                                              PPI_EXAMPLE_TIMER1_INTERVAL),                                    NRF_TIMER_SHORT_COMPARE0_CLEAR_MASK,                                    false); }

/** @brief Function for Timer 2 initialization.  *  @details Initializes TIMER2 peripheral to generate an event every 2 seconds. The events are  *           generated at odd numbers of seconds after starting the example (3, 5, 7 ...) and they  *           are used to start TIMER0 via PPI: TIMER2->EVENT_COMPARE[0] triggers TIMER0->TASK_START.  */ static void timer2_init(void) {     // Check TIMER2 configuration for details.     nrf_drv_timer_config_t timer_cfg = NRF_DRV_TIMER_DEFAULT_CONFIG;     timer_cfg.frequency = NRF_TIMER_FREQ_31250Hz;     ret_code_t err_code = nrf_drv_timer_init(&m_timer2, &timer_cfg, empty_timer_handler);     APP_ERROR_CHECK(err_code);

    nrf_drv_timer_extended_compare(&m_timer2,                                    NRF_TIMER_CC_CHANNEL0,                                    nrf_drv_timer_ms_to_ticks(&m_timer2,                                                              PPI_EXAMPLE_TIMER2_INTERVAL),                                    NRF_TIMER_SHORT_COMPARE0_CLEAR_MASK,                                    false); } 9.主函数处理

/**  * @brief Function for main application entry.  */ int main(void) {     uint32_t err_code;      uint32_t old_val = 0;     bsp_board_init(BSP_INIT_LEDS);

    const app_uart_comm_params_t comm_params =       {           RX_PIN_NUMBER,           TX_PIN_NUMBER,           RTS_PIN_NUMBER,           CTS_PIN_NUMBER,           UART_HWFC,           false, #if defined (UART_PRESENT)           NRF_UART_BAUDRATE_115200 #else           NRF_UARTE_BAUDRATE_115200 #endif       };

    APP_UART_FIFO_INIT(&comm_params,                          UART_RX_BUF_SIZE,                          UART_TX_BUF_SIZE,                          uart_error_handle,                          APP_IRQ_PRIORITY_LOWEST,                          err_code);

    APP_ERROR_CHECK(err_code);

    ppi_init();     timer0_init(); // Timer used to increase m_counter every 100ms.     timer1_init(); // Timer to generate events on even number of seconds - stopping Timer 0     timer2_init(); // Timer to generate events on odd number of seconds - starting Timer 0

    printf("PPI example started.");

    // Start clock.     nrf_drv_timer_enable(&m_timer0);

    /* Below delay is implemented to ensure that Timer0 interrupt will execute before PPI action.      * Please be aware that such solution was tested only in this simple example code. In case      * of more complex systems with higher level interrupts this may lead to not correct timers      * synchronization.      */     nrf_delay_us(5);     nrf_drv_timer_enable(&m_timer1);

    m_counter = (uint32_t)-PPI_EXAMPLE_TIMERS_PHASE_SHIFT_DELAY;

    // Timer 2 will start one second after Timer 1 (m_counter will equal 0 after 1s)     while (m_counter != 0)      {         // just wait     }     nrf_drv_timer_enable(&m_timer2);

    while (true)     {         uint32_t counter = m_counter;         if (old_val != counter)         {             old_val = counter;

            printf("Current count: %u\r\n", counter);                    }     }

}  

关注
打赏
1658017818
查看更多评论
立即登录/注册

微信扫码登录

0.0389s