This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

app_uart_get more than 1 byte

Hi,

I'm using app_uart for communication between different mcu. I can send more than 1 byte like "0x3917015623"  through  changing tx_buffer[0] to tx_buffer[5]. Unfortunately i couldn't recieve the slave devicess message "0x2917013607". I can only get the first byte "0x07". My configuration are the same as uart example. How can i recieve all the message ?. I tried to use serial library but i couldn't initialize. (It gave ERROR 6 NRF_ERROR_NOT_SUPPORTED).

Slave device is sending me a message every second. And i'm calling app_uart_get function every 500 miliseconds.

Here is my uart init;

void uart_error_handle(app_uart_evt_t * p_event)
{
    if (p_event->evt_type == APP_UART_COMMUNICATION_ERROR)
    {
        APP_ERROR_HANDLER(p_event->data.error_communication);
    }
    else if (p_event->evt_type == APP_UART_FIFO_ERROR)
    {
        APP_ERROR_HANDLER(p_event->data.error_code);
    }    
}

void uart_init(void)
{
    uint32_t err_code;
    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_9600
  #endif
        };
//    const app_uart_buffers_t m_buffers =
//      {
//        &rx_buffer_s,
//        sizeof(rx_buffer_s),
//        &tx_buffer_s,
//        sizeof(tx_buffer_s)
//      }
      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);
//      err_code = app_uart_init(&comm_params, &m_buffers, uart_error_handle, APP_IRQ_PRIORITY_LOW);
//      APP_ERROR_CHECK(err_code);
  
}

Regards,

Parents
  • I tried to use serial library but i couldn't initialize. (It gave ERROR 6 NRF_ERROR_NOT_SUPPORTED).

     Which function returned NRF_ERROR_NOT_SUPPORTED?

  • nrf_serial_init function was returning NRF_ERROR_NOT_SUPPORTED. I fixed that error yesterday. I did a lot of things. I couldn't remember exactly but i remember that i changed some code in nrf_serial.c . Now, i can send 5 byte data on TX_PIN  but i received wrong data from slave. Also i am using MAX485 IC for communication. I need to set RTS_PIN before sending operation and clear it before receive operation. But nrf_gpio_pin_set or nrf_gpio_pin_clear command doesn't effect the RTS_PIN. When i deactive UART module then these command are starting to work. When UART module enabled, RTS_PIN goes high at wrong time and out of my control. Time between sending operation and RTS_PIN high is about 95 ms. It should be at the same time. So how can i control RTS pin while UART Module enabled.(I can control other gpio when uart enabled.)

    here is my serial init code:

    NRF_SERIAL_DRV_UART_CONFIG_DEF(m_uart0_drv_config,
                          RX_PIN_NUMBER, TX_PIN_NUMBER,
                          RTS_PIN_NUMBER, CTS_PIN_NUMBER,
                          NRF_UART_HWFC_ENABLED, NRF_UART_PARITY_EXCLUDED,
                          NRF_UART_BAUDRATE_9600,
                          UART_DEFAULT_CONFIG_IRQ_PRIORITY);
    
    #define SERIAL_FIFO_TX_SIZE 32
    #define SERIAL_FIFO_RX_SIZE 32
    
    NRF_SERIAL_QUEUES_DEF(serial_queues, SERIAL_FIFO_TX_SIZE, SERIAL_FIFO_RX_SIZE);
    
    #define SERIAL_BUFF_TX_SIZE 5
    #define SERIAL_BUFF_RX_SIZE 5
    
    NRF_SERIAL_BUFFERS_DEF(serial_buffs, SERIAL_BUFF_TX_SIZE, SERIAL_BUFF_RX_SIZE);
    
    NRF_SERIAL_CONFIG_DEF(serial_config, NRF_SERIAL_MODE_IRQ,
                          &serial_queues, &serial_buffs, NULL, NULL);
    
    
    NRF_SERIAL_UART_DEF(serial_uart, 0);
    
        ret_code_t ret;
    //    ret = nrf_drv_clock_init();
    //    APP_ERROR_CHECK(ret);
    //    ret = nrf_drv_power_init(NULL);
    //    APP_ERROR_CHECK(ret);
    
        nrf_drv_clock_lfclk_request(NULL);
        ret = app_timer_init();
        APP_ERROR_CHECK(ret);
        
        ret = nrf_serial_init(&serial_uart, &m_uart0_drv_config, &serial_config);
        APP_ERROR_CHECK(ret);

  • Is there any example of it ? Would you please explain ".It is possible to schedule application code around the BLE events using the Timeslot API "?. Did you mean scheduler ?

  • We have a tutorial on the Timeslot API. Its based on SDK v11, but the Timeslot API has not changed very much since then so it should still be relevant, see https://devzone.nordicsemi.com/nordic/short-range-guides/b/software-development-kit/posts/setting-up-the-timeslot-api

    The Timeslot API allows the application to request a timeslot where you are guaranteed that there will be no interrupts from the SoftDevice. YOu can perform the UART transaction in the Timeslot to avoid the timeout issues. 

  • Well, i will try it. My Development Kit has broken i guess. I created a new ticket for it. Can i program my Custom Board with ST-Link on STM dev kits?

  • I tried timeslot, actually i am not sure that i did it correct. I got  "<error> app: SOFTDEVICE: ASSERTION FAILED" error. The program is falling error after  serial_timslot.h line : 180

    Q1: where shoul i call timeslot_sd_init() ? Is this function start to my receiving operation ? Should i call it in main just one time or every time when i want to read rx pin?

    serial_timslot.h

    #include <stdint.h>
    #include <stdbool.h>
    #include "nrf.h"
    #include "app_error.h"
    #include "nrf_gpio.h"
    #include "nrf_sdh.h"
    #include "boards.h"
    
    #include "nrf_serial.h"
    #include "nrf_drv_uart.h"
    
    
    
    
    NRF_SERIAL_DRV_UART_CONFIG_DEF(m_uart0_drv_config,
                          RX_PIN_NUMBER, TX_PIN_NUMBER,
                          RTS_PIN_NUMBER, CTS_PIN_NUMBER,
                          NRF_UART_HWFC_DISABLED, NRF_UART_PARITY_EXCLUDED,
                          NRF_UART_BAUDRATE_9600,
                          UART_DEFAULT_CONFIG_IRQ_PRIORITY);
    
    #define SERIAL_FIFO_TX_SIZE 64
    #define SERIAL_FIFO_RX_SIZE 64
    
    NRF_SERIAL_QUEUES_DEF(serial_queues, SERIAL_FIFO_TX_SIZE, SERIAL_FIFO_RX_SIZE);
    
    #define SERIAL_BUFF_TX_SIZE 5
    #define SERIAL_BUFF_RX_SIZE 5
    
    NRF_SERIAL_BUFFERS_DEF(serial_buffs, SERIAL_BUFF_TX_SIZE, SERIAL_BUFF_RX_SIZE);
    
    NRF_SERIAL_CONFIG_DEF(serial_config, NRF_SERIAL_MODE_IRQ,
                          &serial_queues, &serial_buffs, NULL, NULL);
    
    
    NRF_SERIAL_UART_DEF(serial_uart, 0);
    
    uint8_t rx_message[5];
    uint8_t rx_data, rx_data1, rx_data2; 
    int8_t tx_data=0x66; 
    
    
    /**Timeslot API için sabitler
    */
    static nrf_radio_request_t  m_timeslot_request;
    static uint32_t             m_slot_length;
    
    static nrf_radio_signal_callback_return_param_t signal_callback_return_param;
    
    /**Bir sonraki timeslot eventini earliest modda çağır
    */
    uint32_t request_next_event_earliest(void)
    {
        m_slot_length                                  = 100000;
        m_timeslot_request.request_type                = NRF_RADIO_REQ_TYPE_EARLIEST;
        m_timeslot_request.params.earliest.hfclk       = NRF_RADIO_HFCLK_CFG_NO_GUARANTEE;
        m_timeslot_request.params.earliest.priority    = NRF_RADIO_PRIORITY_NORMAL;
        m_timeslot_request.params.earliest.length_us   = m_slot_length;
        m_timeslot_request.params.earliest.timeout_us  = 1000000;
        return sd_radio_request(&m_timeslot_request);
    
    }
    
    /**@brief Configure next timeslot event in earliest configuration
     */
    void configure_next_event_earliest(void)
    {
        m_slot_length                                  = 15000;
        m_timeslot_request.request_type                = NRF_RADIO_REQ_TYPE_EARLIEST;
        m_timeslot_request.params.earliest.hfclk       = NRF_RADIO_HFCLK_CFG_NO_GUARANTEE;
        m_timeslot_request.params.earliest.priority    = NRF_RADIO_PRIORITY_NORMAL;
        m_timeslot_request.params.earliest.length_us   = m_slot_length;
        m_timeslot_request.params.earliest.timeout_us  = 1000000;
    }
    
    /**@brief Configure next timeslot event in normal configuration
     */
    void configure_next_event_normal(void)
    {
        m_slot_length                                 = 100000;
        m_timeslot_request.request_type               = NRF_RADIO_REQ_TYPE_NORMAL;
        m_timeslot_request.params.normal.hfclk        = NRF_RADIO_HFCLK_CFG_NO_GUARANTEE;
        m_timeslot_request.params.normal.priority     = NRF_RADIO_PRIORITY_HIGH;
        m_timeslot_request.params.normal.distance_us  = 100000;
        m_timeslot_request.params.normal.length_us    = m_slot_length;
    }
    
    
    /**@brief Timeslot signal handler
     */
    void nrf_evt_signal_handler(uint32_t evt_id)
    {
        uint32_t err_code;
        
        switch (evt_id)
        {
            case NRF_EVT_RADIO_SIGNAL_CALLBACK_INVALID_RETURN:
                //No implementation needed
                break;
            case NRF_EVT_RADIO_SESSION_IDLE:
                //No implementation needed
                break;
            case NRF_EVT_RADIO_SESSION_CLOSED:
                //No implementation needed, session ended
                break;
            case NRF_EVT_RADIO_BLOCKED:
                //Fall through
            case NRF_EVT_RADIO_CANCELED:
                err_code = request_next_event_earliest();
                APP_ERROR_CHECK(err_code);
                break;
            default:
                break;
        }
    }
    
    
    /**@brief Timeslot event handler
     */
    nrf_radio_signal_callback_return_param_t * radio_callback(uint8_t signal_type)
    {
        switch(signal_type)
        {
            case NRF_RADIO_CALLBACK_SIGNAL_TYPE_START:
                //Start of the timeslot - set up timer interrupt
                signal_callback_return_param.params.request.p_next = NULL;
                signal_callback_return_param.callback_action = NRF_RADIO_SIGNAL_CALLBACK_ACTION_NONE;
                
                NRF_TIMER0->INTENSET = TIMER_INTENSET_COMPARE0_Msk;
                NRF_TIMER0->CC[0] = m_slot_length - 1000;
                NVIC_EnableIRQ(TIMER0_IRQn);
                
    /*-------------------Read UART--------------------------------------*/            
    /*---------------------------------------------------------------------------------------------------*/            
              uint32_t err_code;
              err_code = nrf_serial_read(&serial_uart, &rx_message, sizeof(rx_message), NULL, 0);
              NRF_LOG_INFO("Recieved error : %d \n",err_code);
    //        if(err_code == 13)
    //        {
    //          ret = nrf_serial_uninit(&serial_uart);
    //          APP_ERROR_CHECK(ret);
    //          nrf_delay_ms(10);
    //          ret = nrf_serial_init(&serial_uart, &m_uart0_drv_config, &serial_config);
    //          APP_ERROR_CHECK(ret);
    //          
    //        }
            (void)nrf_serial_flush(&serial_uart, 0);
              if(rx_message[3]>0)
                  NRF_LOG_INFO("Recieved data : %d \n", rx_message[3]);
                  rx_message[3] = rx_data;        
            //   err_code = 0;
    /*---------------------------------------------------------------------------------------------------*/ 
                break;
    
            case NRF_RADIO_CALLBACK_SIGNAL_TYPE_RADIO:
                signal_callback_return_param.params.request.p_next = NULL;
                signal_callback_return_param.callback_action = NRF_RADIO_SIGNAL_CALLBACK_ACTION_NONE;
                break;
    
            case NRF_RADIO_CALLBACK_SIGNAL_TYPE_TIMER0:
                //Timer interrupt - do graceful shutdown - schedule next timeslot
                configure_next_event_normal();
                signal_callback_return_param.params.request.p_next = &m_timeslot_request;
                signal_callback_return_param.callback_action = NRF_RADIO_SIGNAL_CALLBACK_ACTION_REQUEST_AND_END;
                break;
            case NRF_RADIO_CALLBACK_SIGNAL_TYPE_EXTEND_SUCCEEDED:
                //No implementation needed
                break;
            case NRF_RADIO_CALLBACK_SIGNAL_TYPE_EXTEND_FAILED:
                //Try scheduling a new timeslot
                configure_next_event_earliest();
                signal_callback_return_param.params.request.p_next = &m_timeslot_request;
                signal_callback_return_param.callback_action = NRF_RADIO_SIGNAL_CALLBACK_ACTION_REQUEST_AND_END;
                break;
            default:
                //No implementation needed
                break;
        }
        return (&signal_callback_return_param);
    }//After this line, i got SD ASSERTION ERROR
    
    
    /**@brief Function for initializing the timeslot API.
     */
    uint32_t timeslot_sd_init(void)
    {
        uint32_t err_code;
        
        err_code = sd_radio_session_open(radio_callback);
        if (err_code != NRF_SUCCESS)
        {
            return err_code;
        }
        
        err_code = request_next_event_earliest();
        if (err_code != NRF_SUCCESS)
        {
            (void)sd_radio_session_close();
            return err_code;
        }
        return NRF_SUCCESS;
    }

    main.c

    /**@brief Function for application main entry.
     */
    int main(void)
    {
        ret_code_t rc;
        ret_code_t ret;
        bool erase_bonds;
        
        // Initialize.
        
            log_init();
        power_management_init();
        
        saadc_init();
        timers_init();
        timer_internal_init();
        ble_stack_init();
        gap_params_init();
        gatt_init();
        services_init();
        advertising_init();
        conn_params_init();
        app_buttons_init(); 
        //uart_init();  //UART ile NRF_LOG Modülleri aynı anda kullanılamıyor. NRF_LOG modülü devredışı bırakıldı.
        
        ret = nrf_serial_init(&serial_uart, &m_uart0_drv_config, &serial_config);
        APP_ERROR_CHECK(ret);
        gpio_init();
        timeslot_sd_init();
    
    //    ret = nrf_drv_clock_init();
    //    APP_ERROR_CHECK(ret);
    //    ret = nrf_drv_power_init(NULL);
    //    APP_ERROR_CHECK(ret);
    
    //    nrf_drv_clock_lfclk_request(NULL);
    //    ret = app_timer_init();
    //    APP_ERROR_CHECK(ret);
        
    
    
        uint8_t message[] = {0x29,0x17,0x01,0x52,0x6D};
        uint8_t rx_message[5];
        
        // Start execution.
        advertising_start(erase_bonds);
         /* Register first to receive an event when initialization is complete. */
        (void) fds_register(fds_evt_handler);
        rc = fds_init();
        APP_ERROR_CHECK(rc);
        
      /* Wait for fds to initialize. */
         wait_for_fds_ready();
    
         motor_delay = record_read(MOTOR_DELAY_FILE_ID,MOTOR_DELAY_KEY);
         uint8_t rx_data, rx_data1, rx_data2; 
         int8_t tx_data=0x66; 
    
         NRF_LOG_INFO("FDS_REGISTER complete."); 
    
    //     delete_all_process();
    //     wait_for_fds_ready();
        // Enter main loop.
        for (;;)
        {
            idle_state_handle();
            
            if(timer_overflow >=5)
            {
              timer_overflow=0;
              ++timer_overflow_2;
             /*10_ms operations*/
             
             
             
         
             
    
             
                
            }
    
            if(timer_overflow_2 >=10)
            {
              ++timer_overflow_3;
              timer_overflow_2=0;
              
                
              
             /*100_ms operations*/         
                  if(button_motor_flag == true)
                  {
                    nrf_gpio_pin_set(RELAY_1);
                  }
                  else
                  {
                    nrf_gpio_pin_clear(RELAY_1);
                  }
    
                  if(button_lamba_flag == true)
                  {
                    nrf_gpio_pin_set(RELAY_2);
                  }
                  else
                  {
                    nrf_gpio_pin_clear(RELAY_2);
    
                  }
                  
                
    
    
            } 
    
            
              
    
            if(timer_overflow_3 >= 5)
            {
              ++timer_overflow_4;
              timer_overflow_3=0; 
              /* 500 ms lik ilemler*/
    
              ++motor_delay_counter;
    
              our_sensor_characteristic_update(&m_our_service, &SIGNAL_IN);
              our_trm_error_characteristic_update_2(&m_our_service, &TRM_IN);
              
              
    //          uint32_t err_code;
    //          
    //          err_code = nrf_serial_write(&serial_uart, &message, sizeof(message), NULL, 100);
    //          ++message[3];
    //          (void)nrf_serial_flush(&serial_uart, 0);
    
    
    
    
              if((motor_delay_counter > motor_delay) && (motor_stop_flag == false))      
             {
                
                  nrf_gpio_pin_set(MOTOR);
                  motor_delay_counter = 0;
                  // nrf_gpio_pin_set(TX_PIN_NUMBER);
                               
             }
     
    
    
    ////////////////////////////////////////
    //  LIGHT STATUS EKLENECEK
    /////////////////////////////////////// 
    
            }
            
    
            if(timer_overflow_4 >= 2)
            {
              timer_overflow_4 = 0;
              /*1 sn lik ilemler */
              ret_code_t ret_code;
              
    //          uint32_t err_code;
    // 
    //          err_code = nrf_serial_read(&serial_uart, &rx_message, sizeof(rx_message), NULL, 100);
    //        NRF_LOG_INFO("Recieved error : %d \n",err_code);
    //        if(err_code == 13)
    //        {
    //          ret = nrf_serial_uninit(&serial_uart);
    //          APP_ERROR_CHECK(ret);
    //          nrf_delay_ms(10);
    //          ret = nrf_serial_init(&serial_uart, &m_uart0_drv_config, &serial_config);
    //          APP_ERROR_CHECK(ret);
    //          
    //        }
    //        (void)nrf_serial_flush(&serial_uart, 0);
    //          if(rx_message[3]>0)
    //              NRF_LOG_INFO("Recieved data : %d \n", rx_message[3]);
    //              rx_message[3] = rx_data;
    //        //     our_rx_characteristic_update(&m_our_service, &rx_data);
    //           err_code = 0;
    //        
              delete_record(MOTOR_DELAY_FILE_ID,MOTOR_DELAY_KEY);
              wait_for_fds_ready();
              record_write(MOTOR_DELAY_FILE_ID,MOTOR_DELAY_KEY,&motor_delay);
              wait_for_fds_ready();
              //show_stats();
            }
    
        }
    }
    
    
    /**
     * @}
     */

Reply
  • I tried timeslot, actually i am not sure that i did it correct. I got  "<error> app: SOFTDEVICE: ASSERTION FAILED" error. The program is falling error after  serial_timslot.h line : 180

    Q1: where shoul i call timeslot_sd_init() ? Is this function start to my receiving operation ? Should i call it in main just one time or every time when i want to read rx pin?

    serial_timslot.h

    #include <stdint.h>
    #include <stdbool.h>
    #include "nrf.h"
    #include "app_error.h"
    #include "nrf_gpio.h"
    #include "nrf_sdh.h"
    #include "boards.h"
    
    #include "nrf_serial.h"
    #include "nrf_drv_uart.h"
    
    
    
    
    NRF_SERIAL_DRV_UART_CONFIG_DEF(m_uart0_drv_config,
                          RX_PIN_NUMBER, TX_PIN_NUMBER,
                          RTS_PIN_NUMBER, CTS_PIN_NUMBER,
                          NRF_UART_HWFC_DISABLED, NRF_UART_PARITY_EXCLUDED,
                          NRF_UART_BAUDRATE_9600,
                          UART_DEFAULT_CONFIG_IRQ_PRIORITY);
    
    #define SERIAL_FIFO_TX_SIZE 64
    #define SERIAL_FIFO_RX_SIZE 64
    
    NRF_SERIAL_QUEUES_DEF(serial_queues, SERIAL_FIFO_TX_SIZE, SERIAL_FIFO_RX_SIZE);
    
    #define SERIAL_BUFF_TX_SIZE 5
    #define SERIAL_BUFF_RX_SIZE 5
    
    NRF_SERIAL_BUFFERS_DEF(serial_buffs, SERIAL_BUFF_TX_SIZE, SERIAL_BUFF_RX_SIZE);
    
    NRF_SERIAL_CONFIG_DEF(serial_config, NRF_SERIAL_MODE_IRQ,
                          &serial_queues, &serial_buffs, NULL, NULL);
    
    
    NRF_SERIAL_UART_DEF(serial_uart, 0);
    
    uint8_t rx_message[5];
    uint8_t rx_data, rx_data1, rx_data2; 
    int8_t tx_data=0x66; 
    
    
    /**Timeslot API için sabitler
    */
    static nrf_radio_request_t  m_timeslot_request;
    static uint32_t             m_slot_length;
    
    static nrf_radio_signal_callback_return_param_t signal_callback_return_param;
    
    /**Bir sonraki timeslot eventini earliest modda çağır
    */
    uint32_t request_next_event_earliest(void)
    {
        m_slot_length                                  = 100000;
        m_timeslot_request.request_type                = NRF_RADIO_REQ_TYPE_EARLIEST;
        m_timeslot_request.params.earliest.hfclk       = NRF_RADIO_HFCLK_CFG_NO_GUARANTEE;
        m_timeslot_request.params.earliest.priority    = NRF_RADIO_PRIORITY_NORMAL;
        m_timeslot_request.params.earliest.length_us   = m_slot_length;
        m_timeslot_request.params.earliest.timeout_us  = 1000000;
        return sd_radio_request(&m_timeslot_request);
    
    }
    
    /**@brief Configure next timeslot event in earliest configuration
     */
    void configure_next_event_earliest(void)
    {
        m_slot_length                                  = 15000;
        m_timeslot_request.request_type                = NRF_RADIO_REQ_TYPE_EARLIEST;
        m_timeslot_request.params.earliest.hfclk       = NRF_RADIO_HFCLK_CFG_NO_GUARANTEE;
        m_timeslot_request.params.earliest.priority    = NRF_RADIO_PRIORITY_NORMAL;
        m_timeslot_request.params.earliest.length_us   = m_slot_length;
        m_timeslot_request.params.earliest.timeout_us  = 1000000;
    }
    
    /**@brief Configure next timeslot event in normal configuration
     */
    void configure_next_event_normal(void)
    {
        m_slot_length                                 = 100000;
        m_timeslot_request.request_type               = NRF_RADIO_REQ_TYPE_NORMAL;
        m_timeslot_request.params.normal.hfclk        = NRF_RADIO_HFCLK_CFG_NO_GUARANTEE;
        m_timeslot_request.params.normal.priority     = NRF_RADIO_PRIORITY_HIGH;
        m_timeslot_request.params.normal.distance_us  = 100000;
        m_timeslot_request.params.normal.length_us    = m_slot_length;
    }
    
    
    /**@brief Timeslot signal handler
     */
    void nrf_evt_signal_handler(uint32_t evt_id)
    {
        uint32_t err_code;
        
        switch (evt_id)
        {
            case NRF_EVT_RADIO_SIGNAL_CALLBACK_INVALID_RETURN:
                //No implementation needed
                break;
            case NRF_EVT_RADIO_SESSION_IDLE:
                //No implementation needed
                break;
            case NRF_EVT_RADIO_SESSION_CLOSED:
                //No implementation needed, session ended
                break;
            case NRF_EVT_RADIO_BLOCKED:
                //Fall through
            case NRF_EVT_RADIO_CANCELED:
                err_code = request_next_event_earliest();
                APP_ERROR_CHECK(err_code);
                break;
            default:
                break;
        }
    }
    
    
    /**@brief Timeslot event handler
     */
    nrf_radio_signal_callback_return_param_t * radio_callback(uint8_t signal_type)
    {
        switch(signal_type)
        {
            case NRF_RADIO_CALLBACK_SIGNAL_TYPE_START:
                //Start of the timeslot - set up timer interrupt
                signal_callback_return_param.params.request.p_next = NULL;
                signal_callback_return_param.callback_action = NRF_RADIO_SIGNAL_CALLBACK_ACTION_NONE;
                
                NRF_TIMER0->INTENSET = TIMER_INTENSET_COMPARE0_Msk;
                NRF_TIMER0->CC[0] = m_slot_length - 1000;
                NVIC_EnableIRQ(TIMER0_IRQn);
                
    /*-------------------Read UART--------------------------------------*/            
    /*---------------------------------------------------------------------------------------------------*/            
              uint32_t err_code;
              err_code = nrf_serial_read(&serial_uart, &rx_message, sizeof(rx_message), NULL, 0);
              NRF_LOG_INFO("Recieved error : %d \n",err_code);
    //        if(err_code == 13)
    //        {
    //          ret = nrf_serial_uninit(&serial_uart);
    //          APP_ERROR_CHECK(ret);
    //          nrf_delay_ms(10);
    //          ret = nrf_serial_init(&serial_uart, &m_uart0_drv_config, &serial_config);
    //          APP_ERROR_CHECK(ret);
    //          
    //        }
            (void)nrf_serial_flush(&serial_uart, 0);
              if(rx_message[3]>0)
                  NRF_LOG_INFO("Recieved data : %d \n", rx_message[3]);
                  rx_message[3] = rx_data;        
            //   err_code = 0;
    /*---------------------------------------------------------------------------------------------------*/ 
                break;
    
            case NRF_RADIO_CALLBACK_SIGNAL_TYPE_RADIO:
                signal_callback_return_param.params.request.p_next = NULL;
                signal_callback_return_param.callback_action = NRF_RADIO_SIGNAL_CALLBACK_ACTION_NONE;
                break;
    
            case NRF_RADIO_CALLBACK_SIGNAL_TYPE_TIMER0:
                //Timer interrupt - do graceful shutdown - schedule next timeslot
                configure_next_event_normal();
                signal_callback_return_param.params.request.p_next = &m_timeslot_request;
                signal_callback_return_param.callback_action = NRF_RADIO_SIGNAL_CALLBACK_ACTION_REQUEST_AND_END;
                break;
            case NRF_RADIO_CALLBACK_SIGNAL_TYPE_EXTEND_SUCCEEDED:
                //No implementation needed
                break;
            case NRF_RADIO_CALLBACK_SIGNAL_TYPE_EXTEND_FAILED:
                //Try scheduling a new timeslot
                configure_next_event_earliest();
                signal_callback_return_param.params.request.p_next = &m_timeslot_request;
                signal_callback_return_param.callback_action = NRF_RADIO_SIGNAL_CALLBACK_ACTION_REQUEST_AND_END;
                break;
            default:
                //No implementation needed
                break;
        }
        return (&signal_callback_return_param);
    }//After this line, i got SD ASSERTION ERROR
    
    
    /**@brief Function for initializing the timeslot API.
     */
    uint32_t timeslot_sd_init(void)
    {
        uint32_t err_code;
        
        err_code = sd_radio_session_open(radio_callback);
        if (err_code != NRF_SUCCESS)
        {
            return err_code;
        }
        
        err_code = request_next_event_earliest();
        if (err_code != NRF_SUCCESS)
        {
            (void)sd_radio_session_close();
            return err_code;
        }
        return NRF_SUCCESS;
    }

    main.c

    /**@brief Function for application main entry.
     */
    int main(void)
    {
        ret_code_t rc;
        ret_code_t ret;
        bool erase_bonds;
        
        // Initialize.
        
            log_init();
        power_management_init();
        
        saadc_init();
        timers_init();
        timer_internal_init();
        ble_stack_init();
        gap_params_init();
        gatt_init();
        services_init();
        advertising_init();
        conn_params_init();
        app_buttons_init(); 
        //uart_init();  //UART ile NRF_LOG Modülleri aynı anda kullanılamıyor. NRF_LOG modülü devredışı bırakıldı.
        
        ret = nrf_serial_init(&serial_uart, &m_uart0_drv_config, &serial_config);
        APP_ERROR_CHECK(ret);
        gpio_init();
        timeslot_sd_init();
    
    //    ret = nrf_drv_clock_init();
    //    APP_ERROR_CHECK(ret);
    //    ret = nrf_drv_power_init(NULL);
    //    APP_ERROR_CHECK(ret);
    
    //    nrf_drv_clock_lfclk_request(NULL);
    //    ret = app_timer_init();
    //    APP_ERROR_CHECK(ret);
        
    
    
        uint8_t message[] = {0x29,0x17,0x01,0x52,0x6D};
        uint8_t rx_message[5];
        
        // Start execution.
        advertising_start(erase_bonds);
         /* Register first to receive an event when initialization is complete. */
        (void) fds_register(fds_evt_handler);
        rc = fds_init();
        APP_ERROR_CHECK(rc);
        
      /* Wait for fds to initialize. */
         wait_for_fds_ready();
    
         motor_delay = record_read(MOTOR_DELAY_FILE_ID,MOTOR_DELAY_KEY);
         uint8_t rx_data, rx_data1, rx_data2; 
         int8_t tx_data=0x66; 
    
         NRF_LOG_INFO("FDS_REGISTER complete."); 
    
    //     delete_all_process();
    //     wait_for_fds_ready();
        // Enter main loop.
        for (;;)
        {
            idle_state_handle();
            
            if(timer_overflow >=5)
            {
              timer_overflow=0;
              ++timer_overflow_2;
             /*10_ms operations*/
             
             
             
         
             
    
             
                
            }
    
            if(timer_overflow_2 >=10)
            {
              ++timer_overflow_3;
              timer_overflow_2=0;
              
                
              
             /*100_ms operations*/         
                  if(button_motor_flag == true)
                  {
                    nrf_gpio_pin_set(RELAY_1);
                  }
                  else
                  {
                    nrf_gpio_pin_clear(RELAY_1);
                  }
    
                  if(button_lamba_flag == true)
                  {
                    nrf_gpio_pin_set(RELAY_2);
                  }
                  else
                  {
                    nrf_gpio_pin_clear(RELAY_2);
    
                  }
                  
                
    
    
            } 
    
            
              
    
            if(timer_overflow_3 >= 5)
            {
              ++timer_overflow_4;
              timer_overflow_3=0; 
              /* 500 ms lik ilemler*/
    
              ++motor_delay_counter;
    
              our_sensor_characteristic_update(&m_our_service, &SIGNAL_IN);
              our_trm_error_characteristic_update_2(&m_our_service, &TRM_IN);
              
              
    //          uint32_t err_code;
    //          
    //          err_code = nrf_serial_write(&serial_uart, &message, sizeof(message), NULL, 100);
    //          ++message[3];
    //          (void)nrf_serial_flush(&serial_uart, 0);
    
    
    
    
              if((motor_delay_counter > motor_delay) && (motor_stop_flag == false))      
             {
                
                  nrf_gpio_pin_set(MOTOR);
                  motor_delay_counter = 0;
                  // nrf_gpio_pin_set(TX_PIN_NUMBER);
                               
             }
     
    
    
    ////////////////////////////////////////
    //  LIGHT STATUS EKLENECEK
    /////////////////////////////////////// 
    
            }
            
    
            if(timer_overflow_4 >= 2)
            {
              timer_overflow_4 = 0;
              /*1 sn lik ilemler */
              ret_code_t ret_code;
              
    //          uint32_t err_code;
    // 
    //          err_code = nrf_serial_read(&serial_uart, &rx_message, sizeof(rx_message), NULL, 100);
    //        NRF_LOG_INFO("Recieved error : %d \n",err_code);
    //        if(err_code == 13)
    //        {
    //          ret = nrf_serial_uninit(&serial_uart);
    //          APP_ERROR_CHECK(ret);
    //          nrf_delay_ms(10);
    //          ret = nrf_serial_init(&serial_uart, &m_uart0_drv_config, &serial_config);
    //          APP_ERROR_CHECK(ret);
    //          
    //        }
    //        (void)nrf_serial_flush(&serial_uart, 0);
    //          if(rx_message[3]>0)
    //              NRF_LOG_INFO("Recieved data : %d \n", rx_message[3]);
    //              rx_message[3] = rx_data;
    //        //     our_rx_characteristic_update(&m_our_service, &rx_data);
    //           err_code = 0;
    //        
              delete_record(MOTOR_DELAY_FILE_ID,MOTOR_DELAY_KEY);
              wait_for_fds_ready();
              record_write(MOTOR_DELAY_FILE_ID,MOTOR_DELAY_KEY,&motor_delay);
              wait_for_fds_ready();
              //show_stats();
            }
    
        }
    }
    
    
    /**
     * @}
     */

Children
  • HI Mehmet, 

    as stated in step 10 of the tutorial

    1. Add timeslot_sd_init(); to main().

    It should be added after ble_stack_init() so your main() function looks good.  When you call timeslot_sd_init() you should get a NRF_RADIO_CALLBACK_SIGNAL_TYPE_START event indicating that the Timeslot is open and you should get the NRF_RADIO_CALLBACK_SIGNAL_TYPE_TIMER0 event 100us before the slot ends. 

    One change I you will have to do is to add the following line to timeslot.c after the definition of radio_callback. 

    NRF_SDH_SOC_OBSERVER(m_signal_evt_observer, 0, nrf_evt_signal_handler, NULL);

    This replaces step 8 in the tutorial and is needed since we have changed our event dispatch system in the newer SDKs. 

    Best regards

    Bjørn

  • NRF_RADIO_CALLBACK_SIGNAL_TYPE_START event indicating that the Timeslot is open and you should get the NRF_RADIO_CALLBACK_SIGNAL_TYPE_TIMER0 event 100us before the slot ends. 

    Yes, these events occurs.

    It started to work after i removed the breakpoints in radio_callback and also i already added this code in main.c

    static void time_slot_soc_evt_handler(uint32_t evt_id, void * p_context)
    {
              (evt_id);
    }
    
    NRF_SDH_SOC_OBSERVER(m_time_slot_soc_observer, 0, time_slot_soc_evt_handler, NULL);
      
    

    When i started to debug with these changes, i can't receive  data continuously. It just enter timeslot one time. So, i added these codes in main.c line 886.

    err_code = request_next_event_earliest();
    if (err_code != NRF_SUCCESS)
    {
      (void)sd_radio_session_close();
      return err_code;
    }

    Then i can receive data countinuously but only between two nrf. Without timeslot i could receive very less correct data from PIC. With timeslot, nrf to nrf is okey but pic to nrf is not working. I can't receive any correct data with timeslot from PIC. I added my whole main.c below.

    #include "Defination.h"
    
    
    static void advertising_start(bool erase_bonds);
    
    /**@brief Function for assert macro callback.
     *
     * @details This function will be called in case of an assert in the SoftDevice.
     *
     * @warning This handler is an example only and does not fit a final product. You need to analyze
     *          how your product is supposed to react in case of Assert.
     * @warning On assert from the SoftDevice, the system can only recover on reset.
     *
     * @param[in] line_num    Line number of the failing ASSERT call.
     * @param[in] p_file_name File name of the failing ASSERT call.
     */
    void assert_nrf_callback(uint16_t line_num, const uint8_t * p_file_name)
    {
        app_error_handler(DEAD_BEEF, line_num, p_file_name);
    }
    
    
    static void time_slot_soc_evt_handler(uint32_t evt_id, void * p_context)
    {
              (evt_id);
    }
    
    NRF_SDH_SOC_OBSERVER(m_time_slot_soc_observer, 0, time_slot_soc_evt_handler, NULL);
      
    
    /**@brief Function for the Timer initialization.
     *
     * @details Initializes the timer module.
     */
    static void timers_init(void)
    {
        // Initialize timer module, making it use the scheduler
        ret_code_t err_code = app_timer_init();
        APP_ERROR_CHECK(err_code);
    }
    
    /**@brief Function for handling advertising events.
     *
     * @details This function will be called for advertising events which are passed to the application.
     *
     * @param[in] ble_adv_evt  Advertising event.
     */
    static void on_adv_evt(ble_adv_evt_t ble_adv_evt)
    {
        ret_code_t err_code;
    
        switch (ble_adv_evt)
        {
            case BLE_ADV_EVT_FAST:
                NRF_LOG_INFO("Fast advertising.");
    //            err_code = bsp_indication_set(BSP_INDICATE_ADVERTISING);
    //            APP_ERROR_CHECK(err_code);
                break;
    
            case BLE_ADV_EVT_IDLE:
    
                break;
    
            default:
                break;
        }
    }
    
    
    /**@brief Function for the GAP initialization.
     *
     * @details This function sets up all the necessary GAP (Generic Access Profile) parameters of the
     *          device including the device name, appearance, and the preferred connection parameters.
     */
    static void gap_params_init(void)
    {
        ret_code_t              err_code;
        ble_gap_conn_params_t   gap_conn_params;
        ble_gap_conn_sec_mode_t sec_mode;
    
        BLE_GAP_CONN_SEC_MODE_SET_OPEN(&sec_mode);
    
        err_code = sd_ble_gap_device_name_set(&sec_mode,
                                              (const uint8_t *)DEVICE_NAME,
                                              strlen(DEVICE_NAME));
        APP_ERROR_CHECK(err_code);
    
        memset(&gap_conn_params, 0, sizeof(gap_conn_params));
    
        gap_conn_params.min_conn_interval = MIN_CONN_INTERVAL;
        gap_conn_params.max_conn_interval = MAX_CONN_INTERVAL;
        gap_conn_params.slave_latency     = SLAVE_LATENCY;
        gap_conn_params.conn_sup_timeout  = CONN_SUP_TIMEOUT;
    
        err_code = sd_ble_gap_ppcp_set(&gap_conn_params);
        APP_ERROR_CHECK(err_code);
    }
    
    
    /**@brief Function for initializing the GATT module.
     */
    static void gatt_init(void)
    {
        ret_code_t err_code = nrf_ble_gatt_init(&m_gatt, NULL);
        APP_ERROR_CHECK(err_code);
    }
    
    
    /**@brief Function for initializing the Advertising functionality.
     *
     * @details Encodes the required advertising data and passes it to the stack.
     *          Also builds a structure to be passed to the stack when starting advertising.
     */
    static void advertising_init(void)
    {
        ret_code_t             err_code;
        ble_advertising_init_t init;
    
        memset(&init, 0, sizeof(init));
    
        init.advdata.name_type               = BLE_ADVDATA_FULL_NAME;
        init.advdata.include_appearance      = true;
        init.advdata.flags                   = BLE_GAP_ADV_FLAGS_LE_ONLY_GENERAL_DISC_MODE;
       
    
    	
    		init.srdata.uuids_complete.uuid_cnt = sizeof(m_adv_uuids) / sizeof(m_adv_uuids[0]);
    		init.srdata.uuids_complete.p_uuids = m_adv_uuids;
    		
    	
        init.config.ble_adv_fast_enabled  = true;
        init.config.ble_adv_fast_interval = APP_ADV_INTERVAL;
        //init.config.ble_adv_fast_timeout  = APP_ADV_DURATION; //SREKL ADVCERTISING YAPMASINI STYORSAK DEVRE DII BIRAKILMALI
    
        init.evt_handler = on_adv_evt;
    
        err_code = ble_advertising_init(&m_advertising, &init);
        APP_ERROR_CHECK(err_code);
    
        ble_advertising_conn_cfg_tag_set(&m_advertising, APP_BLE_CONN_CFG_TAG);
    }
    
    
    /**@brief Function for handling Queued Write Module errors.
     *
     * @details A pointer to this function will be passed to each service which may need to inform the
     *          application about an error.
     *
     * @param[in]   nrf_error   Error code containing information about what went wrong.
     */
    static void nrf_qwr_error_handler(uint32_t nrf_error)
    {
        APP_ERROR_HANDLER(nrf_error);
    }
    
    
    
    /**@brief Function for initializing services that will be used by the application.
     */
    static void services_init(void)
    {
    
    	
        uint32_t         err_code;
        nrf_ble_qwr_init_t qwr_init = {0};
    
        // Initialize Queued Write Module.
        qwr_init.error_handler = nrf_qwr_error_handler;
    
        err_code = nrf_ble_qwr_init(&m_qwr, &qwr_init);
        APP_ERROR_CHECK(err_code);
    
        //FROM_SERVICE_TUTORIAL: Add code to initialize the services used by the application.
        our_service_init(&m_our_service);
        //our_service_init_2(&m_our_service_2);
    
    }
    
    
    /**@brief Function for handling the Connection Parameters Module.
     *
     * @details This function will be called for all events in the Connection Parameters Module that
     *          are passed to the application.
     *
     * @note All this function does is to disconnect. This could have been done by simply
     *       setting the disconnect_on_fail config parameter, but instead we use the event
     *       handler mechanism to demonstrate its use.
     *
     * @param[in] p_evt  Event received from the Connection Parameters Module.
     */
    static void on_conn_params_evt(ble_conn_params_evt_t * p_evt)
    {
        ret_code_t err_code;
    
        if (p_evt->evt_type == BLE_CONN_PARAMS_EVT_FAILED)
        {
            err_code = sd_ble_gap_disconnect(m_conn_handle, BLE_HCI_CONN_INTERVAL_UNACCEPTABLE);
            APP_ERROR_CHECK(err_code);
        }
    }
    
    
    /**@brief Function for handling a Connection Parameters error.
     *
     * @param[in] nrf_error  Error code containing information about what went wrong.
     */
    static void conn_params_error_handler(uint32_t nrf_error)
    {
        APP_ERROR_HANDLER(nrf_error);
    }
    
    
    /**@brief Function for initializing the Connection Parameters module.
     */
    static void conn_params_init(void)
    {
        ret_code_t             err_code;
        ble_conn_params_init_t cp_init;
    
        memset(&cp_init, 0, sizeof(cp_init));
    
        cp_init.p_conn_params                  = NULL;
        cp_init.first_conn_params_update_delay = FIRST_CONN_PARAMS_UPDATE_DELAY;
        cp_init.next_conn_params_update_delay  = NEXT_CONN_PARAMS_UPDATE_DELAY;
        cp_init.max_conn_params_update_count   = MAX_CONN_PARAMS_UPDATE_COUNT;
        cp_init.start_on_notify_cccd_handle    = BLE_GATT_HANDLE_INVALID;
        cp_init.disconnect_on_fail             = false;
        cp_init.evt_handler                    = on_conn_params_evt;
        cp_init.error_handler                  = conn_params_error_handler;
    
        err_code = ble_conn_params_init(&cp_init);
        APP_ERROR_CHECK(err_code);
    }
    
    
    /**@brief Function for starting advertising.
     */
    static void advertising_start(bool erase_bonds)
    {
         if (erase_bonds == true)
        {
            delete_bonds();
            // Advertising is started by PM_EVT_PEERS_DELETED_SUCEEDED event
        }
        else
        {
            ret_code_t err_code = ble_advertising_start(&m_advertising, BLE_ADV_MODE_FAST);
    
            APP_ERROR_CHECK(err_code);
        }
    }
    
    void advertising_stop(void)
    {
        ret_code_t err_code = sd_ble_gap_adv_stop(&m_advertising);
        
        APP_ERROR_CHECK(err_code);
    }
    
    
    /**@brief Function for handling BLE events.
     *
     * @param[in]   p_ble_evt   Bluetooth stack event.
     * @param[in]   p_context   Unused.
     */
    static void ble_evt_handler(ble_evt_t const * p_ble_evt, void * p_context)
    {
    ret_code_t err_code = NRF_SUCCESS;
    
              switch (p_ble_evt->header.evt_id)
              {
                  case BLE_GAP_EVT_DISCONNECTED:
                      NRF_LOG_INFO("Disconnected.");
                      // LED indication will be changed when advertising starts.
     
    
                      break;
    
                  case BLE_GAP_EVT_CONNECTED:
                      NRF_LOG_INFO("Connected.");
    //                  err_code = bsp_indication_set(BSP_INDICATE_CONNECTED);
    //                  APP_ERROR_CHECK(err_code);
                      m_conn_handle = p_ble_evt->evt.gap_evt.conn_handle;
                      err_code = nrf_ble_qwr_conn_handle_assign(&m_qwr, m_conn_handle);
                      APP_ERROR_CHECK(err_code);
    
                      break;
    
                  case BLE_GAP_EVT_PHY_UPDATE_REQUEST:
           
                      NRF_LOG_DEBUG("PHY update request.");
                      ble_gap_phys_t const phys =
                      {
                          .rx_phys = BLE_GAP_PHY_AUTO,
                          .tx_phys = BLE_GAP_PHY_AUTO,
                      };
                      err_code = sd_ble_gap_phy_update(p_ble_evt->evt.gap_evt.conn_handle, &phys);
                      APP_ERROR_CHECK(err_code);
                   break;
    
                  case BLE_GATTC_EVT_TIMEOUT:
                      // Disconnect on GATT Client timeout event.
                      NRF_LOG_DEBUG("GATT Client Timeout.");
                      err_code = sd_ble_gap_disconnect(p_ble_evt->evt.gattc_evt.conn_handle,
                                                       BLE_HCI_REMOTE_USER_TERMINATED_CONNECTION);
                      APP_ERROR_CHECK(err_code);
                      break;
    
                  case BLE_GATTS_EVT_TIMEOUT:
                      // Disconnect on GATT Server timeout event.
                      NRF_LOG_DEBUG("GATT Server Timeout.");
                      err_code = sd_ble_gap_disconnect(p_ble_evt->evt.gatts_evt.conn_handle,
                                                       BLE_HCI_REMOTE_USER_TERMINATED_CONNECTION);
                      APP_ERROR_CHECK(err_code);
                      break;
                  
    
    
                  default:
                      // No implementation needed.
                      break;
              }
    }
    
    
    ///**@brief Function for checking button status
    // */
    //void button_status_check(int a,enum button_press *button)
    //{
    //  
    //    switch(a)
    //    {
    //      case 1:
    //        *button = POWER_ON;
    //        break;
    //      case 2:
    //        *button = FIRST_PRESS;
    //        break;
    //      case 3:
    //        *button = SECOND_PRESS;
    //        break;
    //      case 4:
    //        *button = THIRD_PRESS;
    //        break;    
    //    }
    //}
    
    
    /**@brief Function for initializing the BLE stack.
     *
     * @details Initializes the SoftDevice and the BLE event interrupt.
     */
    static void ble_stack_init(void)
    {
    ret_code_t err_code;
    
        err_code = nrf_sdh_enable_request();
        APP_ERROR_CHECK(err_code);
    
        // Configure the BLE stack using the default settings.
    
    
    
        // Fetch the start address of the application RAM.
        uint32_t ram_start = 0;
        
        err_code = nrf_sdh_ble_default_cfg_set(APP_BLE_CONN_CFG_TAG, &ram_start);
        APP_ERROR_CHECK(err_code);
    
        // Enable BLE stack.
        err_code = nrf_sdh_ble_enable(&ram_start);
        APP_ERROR_CHECK(err_code);
    
        // Register a handler for BLE events.
        NRF_SDH_BLE_OBSERVER(m_ble_observer, APP_BLE_OBSERVER_PRIO, ble_our_service_on_ble_evt, &m_our_service);
    
        // Call ble_our_service_on_ble_evt() to do housekeeping of ble connections related to our service and characteristics
        NRF_SDH_BLE_OBSERVER(m_ble_observer_2, APP_BLE_OBSERVER_PRIO, ble_evt_handler, &m_our_service);        //ble_eventlerini gzlemliyor
    
    }
    
    static void button_handler(uint8_t pin_no, uint8_t button_action)
    {
      //Buttonların kaç kez basıldığını göster  
      if(pin_no == BUTTON_ON && button_action == APP_BUTTON_PUSH)
      {
        i++;
        if(i>3){
          i = 0;
        }
        button_status_check(i,&but_ON);    
        button_on_flag = !button_on_flag;
        //nrf_gpio_pin_toggle(LED_ON);
      }
      if(pin_no == BUTTON_OFF && button_action == APP_BUTTON_PUSH)
      {
        j++;
        if(j>3){
          j = 0;
        }
        button_status_check(j,&but_OFF);
        button_off_flag = !button_off_flag;
        //nrf_gpio_pin_toggle(LED_OFF);
      }
      if(pin_no == BUTTON_LAMBA && button_action == APP_BUTTON_PUSH)
      {
        k++;
        if(k>3){
          k = 0;
        }
        button_status_check(k,&but_LAMB);
        button_lamba_flag = !button_lamba_flag;
        nrf_gpio_pin_toggle(LED_LAMBA);          
      }
      if(pin_no == BUTTON_MOTOR && button_action == APP_BUTTON_PUSH)
      {
        l++;
        if(l>3){
          l = 0;
        }
        button_status_check(l,&but_MOT);
        button_motor_flag = !button_motor_flag;
        nrf_gpio_pin_toggle(LED_MOTOR);
      }
      light_status_set();
    }
    
    static void app_buttons_init(void)
    {
      ret_code_t err_code;
      static app_button_cfg_t buttons_cfg[4] = {
        {BUTTON_ON, APP_BUTTON_ACTIVE_LOW, NRF_GPIO_PIN_PULLUP, button_handler},
        {BUTTON_OFF, APP_BUTTON_ACTIVE_LOW, NRF_GPIO_PIN_PULLUP, button_handler},
        {BUTTON_LAMBA, APP_BUTTON_ACTIVE_LOW, NRF_GPIO_PIN_PULLUP, button_handler},
        {BUTTON_MOTOR, APP_BUTTON_ACTIVE_LOW, NRF_GPIO_PIN_PULLUP, button_handler}
      };
      
      err_code = app_button_init(buttons_cfg,4,5);
      APP_ERROR_CHECK(err_code);
    
      err_code = app_button_enable();
      APP_ERROR_CHECK(err_code);
    }
    
    
    
    
    static void log_init(void)
    {
        ret_code_t err_code = NRF_LOG_INIT(NULL);
        APP_ERROR_CHECK(err_code);
    
        NRF_LOG_DEFAULT_BACKENDS_INIT();
    }
    
    
    /**@brief Function for initializing power management.
     */
    static void power_management_init(void)
    {
        ret_code_t err_code;
        err_code = nrf_pwr_mgmt_init();
        APP_ERROR_CHECK(err_code);
    }
    
    
    /**@brief Function for handling the idle state (main loop).
     *
     * @details If there is no pending log operation, then sleep until next the next event occurs.
     */
    static void idle_state_handle(void)
    {
        if (NRF_LOG_PROCESS() == false)
        {
            nrf_pwr_mgmt_run();
        }
    }
    
    
    //2 msn de buraya gelecek
    void timer_event_handler(nrf_timer_event_t event_type, void * p_context)
    {
    
        ++timer_overflow;
        nrf_gpio_pin_clear(PD_OUT);     //active high
        nrf_delay_us(25);
        nrf_gpio_pin_set(PD_OUT);
        nrf_delay_us(15);
    
        SIGNAL_IN = saadc_measure_SENSOR();    //Sensor measurement
        TRM_IN = saadc_measure_TRM();   //sensor error measurement
    
    
    /*-------------------------lm sonucu karar verme koulu-------------------------*/
        if(SIGNAL_IN > 790)               //2.78 V stndeyse engel yok demektir.
          {
            if(accuracy_counter == 0)
            {
    //                nrf_gpio_pin_set(TX_PIN_NUMBER);
    //                nrf_gpio_pin_set(MOTOR);
              motor_stop_flag = false;
            }
            else
              --accuracy_counter;
          }
          else if(SIGNAL_IN < 767)        //2.70 V altndaysa engel var demektir.
          {
            ++accuracy_counter;
            if(accuracy_counter > receiver_sample_counter)
            {
              accuracy_counter = receiver_sample_counter;
    
              nrf_gpio_pin_clear(TX_PIN_NUMBER); //LED i yak
              nrf_gpio_pin_clear(MOTOR);         //MOTOR'u durdur         
              motor_stop_flag = true;               
              motor_delay_counter = 0;
    
            }
          }
    /*------------------------------------------------------------------------------------*/
    /*-----------------------------TRANSMITTER ERROR DETECT-------------------------------*/
         if((TRM_IN < 75)||(TRM_IN > 750))               //0.26 V den kk, 2.63 V dan bykse hata var.
          {
            ++transmitter_detect_counter;
            if(transmitter_detect_counter > transmitter_error_sample_counter)
            {
              transmitter_detect_counter = transmitter_error_sample_counter;
              trm_error_flag = true;
              nrf_gpio_pin_clear(RX_PIN_NUMBER); 
            }
           }
           else                                           // normal alma koulu ise
           {
              if(transmitter_detect_counter > 0)
                --transmitter_detect_counter;
          
              if(transmitter_detect_counter ==0)
              {
                  trm_error_flag = false;
                  nrf_gpio_pin_set(RX_PIN_NUMBER); 
              }
           }
    
          
    /*----------------------------------------------------------------------------*/
    
    }
    
    static void timer_internal_init(void)
    {
        ret_code_t err_code;
        
        // Configure the timer to use the default configuration set in sdk_config.h
        nrf_drv_timer_config_t timer_cfg = NRF_DRV_TIMER_DEFAULT_CONFIG;
        //Initializing the Timer driver
        err_code = nrf_drv_timer_init(&timer0, &timer_cfg, timer_event_handler);
        APP_ERROR_CHECK(err_code);
        
        /*Configure the timer to generate the COMPARE event after 200*1000UL ticks and enable the shortcut that triggers the CLEAR task on every COMPARE event.
            This will */
        nrf_drv_timer_extended_compare(&timer0, NRF_TIMER_CC_CHANNEL0, nrf_drv_timer_ms_to_ticks(&timer0, 2), NRF_TIMER_SHORT_COMPARE0_CLEAR_MASK, true); // Set last argument to false for Task 3
            
        nrf_drv_timer_enable(&timer0);  // Turning on the Timer.
       
    }
    
    
    static void gpio_init(void)
    {
      nrf_gpio_cfg_output(TX_PIN_NUMBER);
      nrf_gpio_cfg_output(RX_PIN_NUMBER);
      nrf_gpio_cfg_output(RTS_PIN_NUMBER);
      nrf_gpio_cfg_output(RELAY_2);
      nrf_gpio_cfg_output(RELAY_1);
      nrf_gpio_cfg_output(MOTOR);
      nrf_gpio_cfg_output(PD_OUT);
      nrf_gpio_cfg_output(LED_OFF);
      nrf_gpio_cfg_output(LED_ON);
      nrf_gpio_cfg_output(LED_LAMBA);
      nrf_gpio_cfg_output(LED_MOTOR);
    
      nrf_gpio_cfg_input(BUTTON_MOTOR,NRF_GPIO_PIN_PULLUP);
      nrf_gpio_cfg_input(BUTTON_ON,NRF_GPIO_PIN_PULLUP);
      nrf_gpio_cfg_input(BUTTON_OFF,NRF_GPIO_PIN_PULLUP);
      nrf_gpio_cfg_input(BUTTON_LAMBA,NRF_GPIO_PIN_PULLUP);
    
    
      nrf_gpio_pin_clear(TX_PIN_NUMBER);
      nrf_gpio_pin_clear(RX_PIN_NUMBER);
    
      nrf_gpio_pin_clear(MOTOR);
      nrf_gpio_pin_set(LED_ON);
      nrf_gpio_pin_set(LED_OFF);
      nrf_gpio_pin_set(LED_LAMBA);
      nrf_gpio_pin_set(LED_MOTOR);
      nrf_gpio_pin_clear(RELAY_1);
      nrf_gpio_pin_set(RELAY_2);
      nrf_gpio_pin_clear(RTS_PIN_NUMBER);   //clear 0 volt
    }
    
    void saadc_event_handler(nrf_drv_saadc_evt_t const * p_event) {
    	// Do nothing, as we use blocking mode
    
    }
    
    int saadc_init()
    {
      
      nrf_saadc_channel_config_t config = NRF_DRV_SAADC_DEFAULT_CHANNEL_CONFIG_SE(NRF_SAADC_INPUT_AIN3);
      nrf_saadc_channel_config_t config_2 = NRF_DRV_SAADC_DEFAULT_CHANNEL_CONFIG_SE(NRF_SAADC_INPUT_AIN1);
      int ret = nrf_drv_saadc_init(NULL, saadc_event_handler);
      if(ret) return ret;
      ret = nrf_drv_saadc_channel_init(3,&config);
      ret = nrf_drv_saadc_channel_init(1,&config_2);
      return ret;
    }
    
    int saadc_measure_SENSOR() 
    {
      nrf_drv_saadc_sample_convert(3,&SIGNAL_IN);
      if(SIGNAL_IN < 0)
        SIGNAL_IN = 0;
      return SIGNAL_IN;
    }
    
    int saadc_measure_TRM()
    {
      nrf_drv_saadc_sample_convert(1, &TRM_IN);
      if(TRM_IN < 0)
        TRM_IN = 0;
      return  TRM_IN;
    }
    
    
    
    
    /****************************************************************************************************/ 
    static void fds_evt_handler(fds_evt_t const * p_evt)
    {
    //    NRF_LOG_INFO("Event: %s received (%s)",
    //                  fds_evt_str[p_evt->id],
    //                  fds_err_str[p_evt->result]);
    
        switch (p_evt->id)
        {
            case FDS_EVT_INIT:
                if (p_evt->result == FDS_SUCCESS)
                {
                    m_fds_initialized = true;
                }
                break;
    
            case FDS_EVT_WRITE:
            {
                if (p_evt->result == FDS_SUCCESS)
                {
    //                NRF_LOG_INFO("Record ID:\t0x%04x",  p_evt->write.record_id);
    //                NRF_LOG_INFO("File ID:\t0x%04x",    p_evt->write.file_id);
    //                NRF_LOG_INFO("Record key:\t0x%04x", p_evt->write.record_key);
                }
            } break;
    
            case FDS_EVT_DEL_RECORD:
            {
                if (p_evt->result == FDS_SUCCESS)
                {
    //                NRF_LOG_INFO("Record ID:\t0x%04x",  p_evt->del.record_id);
    //                NRF_LOG_INFO("File ID:\t0x%04x",    p_evt->del.file_id);
    //                NRF_LOG_INFO("Record key:\t0x%04x", p_evt->del.record_key);
                }
                m_delete_all.pending = false;
            } break;
    
            default:
                break;
        }
    }    
    
    /**@brief   Sleep until an event is received. */
    static void power_manage(void)
    {
    #ifdef SOFTDEVICE_PRESENT
        (void) sd_app_evt_wait();
    #else
        __WFE();
    #endif
    }
    
    /**@brief   Wait for fds to initialize. */
    static void wait_for_fds_ready(void)
    {
        while (!m_fds_initialized)
        {
            power_manage();
        }
    }
    
    
    
    
    /****************************************************************************************************/
    
    
    /**@brief Function for application main entry.
     */
    int main(void)
    {
        ret_code_t rc;
        ret_code_t ret;
        bool erase_bonds;
        
        // Initialize.
        
        log_init();
        power_management_init();
        
        saadc_init();
        timers_init();
        timer_internal_init();
        ble_stack_init();
        gap_params_init();
        gatt_init();
        services_init();
        advertising_init();
        conn_params_init();
        app_buttons_init(); 
        //uart_init();  //UART ile NRF_LOG Modülleri aynı anda kullanılamıyor. NRF_LOG modülü devredışı bırakıldı.
        ret = nrf_serial_init(&serial_uart, &m_uart0_drv_config, &serial_config);
        APP_ERROR_CHECK(ret);
        gpio_init();
        timeslot_sd_init();
        
           
    //    ret = nrf_drv_clock_init();
    //    APP_ERROR_CHECK(ret);
    //    ret = nrf_drv_power_init(NULL);
    //    APP_ERROR_CHECK(ret);
    
    //    nrf_drv_clock_lfclk_request(NULL);
    //    ret = app_timer_init();
    //    APP_ERROR_CHECK(ret);
        
    
    
        uint8_t message[] = {0x29,0x17,0x01,0x52,0x6D};
        uint8_t rx_message[5];
        
        // Start execution.
        advertising_start(erase_bonds);
         /* Register first to receive an event when initialization is complete. */
        (void) fds_register(fds_evt_handler);
        rc = fds_init();
        APP_ERROR_CHECK(rc);
        
      /* Wait for fds to initialize. */
         wait_for_fds_ready();
    
         motor_delay = record_read(MOTOR_DELAY_FILE_ID,MOTOR_DELAY_KEY);
         uint8_t rx_data, rx_data1, rx_data2; 
         int8_t tx_data=0x66; 
    
         NRF_LOG_INFO("FDS_REGISTER complete."); 
    
    //     delete_all_process();
    //     wait_for_fds_ready();
        // Enter main loop.
        for (;;)
        {
            idle_state_handle();
            
            if(timer_overflow >=5)
            {
              timer_overflow=0;
              ++timer_overflow_2;
             /*10_ms operations*/
             
             
             
         
             
    
             
                
            }
    
            if(timer_overflow_2 >=10)
            {
              ++timer_overflow_3;
              timer_overflow_2=0;
              
                
              
             /*100_ms operations*/         
                  if(button_motor_flag == true)
                  {
                    nrf_gpio_pin_set(RELAY_1);
                  }
                  else
                  {
                    nrf_gpio_pin_clear(RELAY_1);
                  }
    
                  if(button_lamba_flag == true)
                  {
                    nrf_gpio_pin_set(RELAY_2);
                  }
                  else
                  {
                    nrf_gpio_pin_clear(RELAY_2);
    
                  }
                  
                
    
    
            } 
    
            
              
    
            if(timer_overflow_3 >= 5)
            {
              ++timer_overflow_4;
              timer_overflow_3=0; 
              /* 500 ms lik ilemler*/
    
              ++motor_delay_counter;
    
              our_sensor_characteristic_update(&m_our_service, &SIGNAL_IN);
              our_trm_error_characteristic_update_2(&m_our_service, &TRM_IN);
              
              
    //          uint32_t err_code;
    //          
    //          err_code = nrf_serial_write(&serial_uart, &message, sizeof(message), NULL, 100);
    //          ++message[3];
    //          (void)nrf_serial_flush(&serial_uart, 0);
    
    
    
    
              if((motor_delay_counter > motor_delay) && (motor_stop_flag == false))      
             {
                
                  nrf_gpio_pin_set(MOTOR);
                  motor_delay_counter = 0;
                  // nrf_gpio_pin_set(TX_PIN_NUMBER);
                               
             }
     
    
    
    ////////////////////////////////////////
    //  LIGHT STATUS EKLENECEK
    /////////////////////////////////////// 
    
            }
            
    
            if(timer_overflow_4 >= 2)
            {
              timer_overflow_4 = 0;
              /*1 sn lik ilemler */
              ret_code_t ret_code;
              
             uint32_t err_code;
    // 
    //          err_code = nrf_serial_read(&serial_uart, &rx_message, sizeof(rx_message), NULL, 100);
    //        NRF_LOG_INFO("Recieved error : %d \n",err_code);
    //        if(err_code == 13)
    //        {
    //          ret = nrf_serial_uninit(&serial_uart);
    //          APP_ERROR_CHECK(ret);
    //          nrf_delay_ms(10);
    //          ret = nrf_serial_init(&serial_uart, &m_uart0_drv_config, &serial_config);
    //          APP_ERROR_CHECK(ret);
    //          
    //        }
    //        (void)nrf_serial_flush(&serial_uart, 0);
    //          if(rx_message[3]>0)
    //              NRF_LOG_INFO("Recieved data : %d \n", rx_message[3]);
    //              rx_message[3] = rx_data;
    //        //     our_rx_characteristic_update(&m_our_service, &rx_data);
    //           err_code = 0;
    //        
              err_code = request_next_event_earliest(); //WITH THIS CODE I CAN READ CONTINUOUSLY
              if (err_code != NRF_SUCCESS)
              {
                  (void)sd_radio_session_close();
                  return err_code;
              }
              delete_record(MOTOR_DELAY_FILE_ID,MOTOR_DELAY_KEY);
              wait_for_fds_ready();
              record_write(MOTOR_DELAY_FILE_ID,MOTOR_DELAY_KEY,&motor_delay);
              wait_for_fds_ready();
              //show_stats();
            }
    
        }
    }
    
    
    /**
     * @}
     */

    EDIT : I almost made it, i feel it Smile. Is there any function to check the data on rx_buffer ? I think the received data is 0 when nrf_serial_read function returns error code 13 (NRF_ERROR_TIMEOUT) or  no data on buffer. I just need when data available on UART RX. Here is my output;

    <info> app: Recieved data : 1 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 2 
    
    <info> app: Recieved data : 3 
    
    <info> app: Recieved data : 4 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 5 
    
    <info> app: Recieved data : 6 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 7 
    
    <info> app: Recieved data : 8 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 9 
    
    <info> app: Recieved data : 10 
    
    <info> app: Recieved data : 11 
    
    <info> app: Recieved data : 12 
    
    <info> app: Recieved data : 13 
    
    <info> app: Recieved data : 14 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 15 
    
    <info> app: Recieved data : 16 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 17 
    
    <info> app: Recieved data : 18 
    
    <info> app: Recieved data : 19 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 20 
    
    <info> app: Recieved data : 21 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 22 
    
    <info> app: Recieved data : 23 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 24 
    
    <info> app: Recieved data : 25 
    
    <info> app: Recieved data : 26 
    
    <info> app: Recieved data : 27 
    
    <info> app: Recieved data : 28 
    
    <info> app: Recieved data : 29 
    
    <info> app: Recieved data : 30 
    
    <info> app: Recieved data : 31 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 32 
    
    <info> app: Recieved data : 33 
    
    <info> app: Recieved data : 34 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 35 
    
    <info> app: Recieved data : 36 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 37 
    
    <info> app: Recieved data : 38 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 39 
    
    <info> app: Recieved data : 40 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 41 
    
    <info> app: Recieved data : 42 
    
    <info> app: Recieved data : 43 
    
    <info> app: Recieved data : 44 
    
    <info> app: Recieved data : 45 
    
    <info> app: Recieved data : 46 
    
    <info> app: Recieved data : 47 
    
    <info> app: Recieved data : 48 
    
    <info> app: Recieved data : 49 
    
    <info> app: Recieved data : 50 
    
    <info> app: Recieved data : 0 
    
    <info> app: Recieved data : 51 
    
    <info> app: Recieved data : 52 
    

  • You will get the NRF_SERIAL_EVENT_RX_DATA event when RX data is available. The nrf_serial module will call the event handler function passed as the _ev_handler argument to the NRF_SERIAL_CONFIG_DEF macro, which is called at the start of main.c.

  • I added this function above the NRF_SERIAL_CONFIG_DEF and set third parameter of it. I ser a breakpoint on  case NRF_SERIAL_EVENT_RX_DATA  but program is not going to the event handler. Did i miss something ?

    static void serial_event_handler(struct nrf_serial_s const * p_serial,
    nrf_serial_event_t event) 
    {
        switch (event)
    	{
    	case NRF_SERIAL_EVENT_TX_DONE:
    	    break;
    	case NRF_SERIAL_EVENT_RX_DATA:
    	    
                    
                  err_code = request_next_event_earliest();
                  if (err_code != NRF_SUCCESS)
                  {
                      (void)sd_radio_session_close();
                      return err_code;
                  }
    
    	    break;
    	case NRF_SERIAL_EVENT_DRV_ERR:
    	    break;
    	case NRF_SERIAL_EVENT_FIFO_ERR:
    	    break;
    	default:
    	    break;
    	}
    	
    }

  • Hmm, can you set a breakpoint  at the NRF_DRV_UART_EVT_RX_DONE case in the uart_event_handler() in nrf_serial.c and see if you hit it?

    static void uart_event_handler(nrf_drv_uart_event_t * p_event, void * p_context)
    {
        uint32_t ret;
        nrf_serial_t const * p_serial = p_context;
    
        switch (p_event->type)
        {
            case NRF_DRV_UART_EVT_RX_DONE:
            {
                nrf_queue_t const * p_rxq =
                        p_serial->p_ctx->p_config->p_queues->p_rxq;
                size_t len = nrf_queue_in(p_rxq,
                                          p_event->data.rxtx.p_data,
                                          p_event->data.rxtx.bytes);
    
                if (len < p_event->data.rxtx.bytes)
                {
                    event_handler(p_serial, NRF_SERIAL_EVENT_FIFO_ERR);
                    break;
                }
    
                if (p_event->data.rxtx.bytes)
                {
                    event_handler(p_serial, NRF_SERIAL_EVENT_RX_DATA);
                }
                nrf_serial_buffers_t const * p_buffs =
                        p_serial->p_ctx->p_config->p_buffers;
    
                ret = nrf_drv_uart_rx(&p_serial->instance,
                                      p_buffs->p_rxb,
                                      p_buffs->rx_size);
                ASSERT(ret == NRF_SUCCESS);
                break;
            }
            case NRF_DRV_UART_EVT_ERROR:
            {
                event_handler(p_serial, NRF_SERIAL_EVENT_DRV_ERR);
                break;
            }
            case NRF_DRV_UART_EVT_TX_DONE:
            {
                nrf_queue_t const * p_txq =
                        p_serial->p_ctx->p_config->p_queues->p_txq;
                nrf_serial_buffers_t const * p_buffs =
                        p_serial->p_ctx->p_config->p_buffers;
    
                event_handler(p_serial, NRF_SERIAL_EVENT_TX_DONE);
                size_t len = nrf_queue_out(p_txq, p_buffs->p_txb, p_buffs->tx_size);
                if (len == 0)
                {
                    break;
                }
    
                ret = nrf_drv_uart_tx(&p_serial->instance, p_buffs->p_txb, len);
                ASSERT(ret == NRF_SUCCESS);
                break;
            }
            default:
                break;
        }
    }

    Best regards

    Bjørn

Related