NRF52805 custom PCB Radio is not working

Hi all,

We have designed a custom board including a NRF52805 chip. We also followed PCB design guidelines and used the exact PCB layout recommended by Nordic. As expected all the peripherals work but when testing for BLE it doesn't emit any BLE packet. I have attached the test code for BLE. I used the Android application "NRF Connect" to scan for the device. But it is non-discoverable. (I used the same application to debug NRF52832 devices and it discovered them successfully)


#include <stdbool.h>
#include <stdint.h>
#include <stdio.h>
#include <string.h>

#include "nrf_log.h"
#include "nrf_log_ctrl.h"
#include "nrf_log_default_backends.h"

#include "app_timer.h"

#include "nrf.h"
#include "nrf_gpio.h"
#include "nrf_drv_rtc.h"
#include "nrf_drv_clock.h"
#include "nrf_drv_saadc.h"
#include "nrf_drv_ppi.h"
#include "nrf_drv_timer.h"
#include "nrf_delay.h"

#include "nrf_sdh.h"
#include "nrf_sdh_ble.h"
#include "nrf_sdh_soc.h"

#include "nrf_ble_qwr.h"
#include "nrf_ble_gatt.h"
#include "ble_advdata.h"
#include "ble_advertising.h"
#include "ble_conn_params.h"

#include "boards.h"
#include "bsp.h"
#include "app_error.h"
#include "app_util_platform.h"
#include "nrf_pwr_mgmt.h"

#define led 20

#define APP_BLE_CONN_CFG_TAG 1
#define APP_BLE_OBSERVER_PRIO 3

#define DEVICE_NAME "BLE_ANT_TEST"

#define MIN_CONN_INTERVAL MSEC_TO_UNITS(100, UNIT_1_25_MS)
#define MAX_CONN_INTERVAL MSEC_TO_UNITS(200, UNIT_1_25_MS)
#define SLAVE_LSTENCY 0
#define CONN_SUP_TIMEOUT MSEC_TO_UNITS(2000, UNIT_10_MS)

#define FIRST_CONN_PARAMS_UPDATE_DELAY APP_TIMER_TICKS(5000)
#define NEXT_CONN_PARAMS_UPDATE_DELAY APP_TIMER_TICKS(3000)
#define MAX_CONN_PARAMS_UPDATE_COUNT 3

#define APP_ADV_INTERVAL 32                                    //Advertisment interval = 300 x 0.625 =187.5 mS
#define APP_ADV_DURATION 0                                      // Advertisement duration = t x 10mS,  if it is 0 the Duration will be infinite

uint8_t payload = 10;


NRF_BLE_QWR_DEF(m_qwr);
NRF_BLE_GATT_DEF(m_gatt);
BLE_ADVERTISING_DEF(m_advertising);


static uint16_t m_conn_handle = BLE_CONN_HANDLE_INVALID;



static void gap_params_init(void)                                                                         //Initialize GAP(Generic Access Profile)
{
  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);

  err_code = sd_ble_gap_appearance_set(BLE_APPEARANCE_GENERIC_DISPLAY);                  //set the device appearance
  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_LSTENCY;
  gap_conn_params.conn_sup_timeout = CONN_SUP_TIMEOUT;

  err_code = sd_ble_gap_ppcp_set(&gap_conn_params);
  APP_ERROR_CHECK(err_code);
}


static void gatt_init(void)                                                                                //GATT initialization
{
  ret_code_t err_code = nrf_ble_gatt_init(&m_gatt, NULL);             
  APP_ERROR_CHECK(err_code);
}


static void nrf_qwr_error_handler(uint32_t nrf_error)                                                       //Error handler for queue writer
{
  APP_ERROR_HANDLER(nrf_error);
}



static void services_init(void)                                                                             //Initialize the services
{
  ret_code_t err_code;

  nrf_ble_qwr_init_t qwr_init = {0};

  qwr_init.error_handler = nrf_qwr_error_handler;

  err_code = nrf_ble_qwr_init(&m_qwr, &qwr_init);
  APP_ERROR_CHECK(err_code);

}


static void on_conn_params_evt(ble_conn_params_evt_t * p_evt)                                               //Create an event handler for connection parameters update
{
  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);
  }

  if(p_evt->evt_type == BLE_CONN_PARAMS_EVT_SUCCEEDED)
  {
    
  }
}



static void conn_params_error_handler(uint32_t nrf_error)                                               //Error handler for conn params update
{
  APP_ERROR_HANDLER(nrf_error);
}


static void conn_params_init(void)                                                                      //Create a function for setting up the connection parameters
{
  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.error_handler = conn_params_error_handler;
  cp_init.evt_handler = on_conn_params_evt;

  err_code = ble_conn_params_init(&cp_init);
  APP_ERROR_CHECK(err_code);

}


static void on_adv_evt(ble_adv_evt_t ble_adv_evt)                                                       //Advertising event handler
{

  switch (ble_adv_evt) 
  {
    case BLE_ADV_EVT_FAST:                                                    //Fast advertising event
    NRF_LOG_INFO("Fast advertising...");
  
    break;

    case BLE_ADV_EVT_IDLE:                                               //Idle state
   
    sd_nvic_SystemReset();
        
    break;

    default:
    break;
  
  }

}



static void advertising_init(void)                                                                      //Initialize advertising
{
  ret_code_t err_code;
  ble_advertising_init_t init;

  //printf("Data sending\r\n");
  nrf_gpio_pin_toggle(led);
  nrf_delay_ms(1000);
                                  
  uint8_t sensor_read = 90;         //Array of sensor values                                   

  ble_advdata_service_data_t service_data;

  memset(&init, 0, sizeof(init));

  init.advdata.name_type = BLE_ADVDATA_FULL_NAME;
  init.advdata.include_appearance = true;

  service_data.service_uuid = BLE_UUID_DEVICE_INFORMATION_SERVICE;         //Initialize device information service
  service_data.data.size = sizeof(sensor_read);
  service_data.data.p_data = &sensor_read;

  init.advdata.p_service_data_array = &service_data;
  init.advdata.service_data_count = 1;

  init.advdata.flags = BLE_GAP_ADV_FLAGS_LE_ONLY_GENERAL_DISC_MODE;

  init.config.ble_adv_fast_enabled = true;                            //Activate fast advertising
  init.config.ble_adv_on_disconnect_disabled = true;


  init.config.ble_adv_fast_interval = APP_ADV_INTERVAL;
  init.config.ble_adv_fast_timeout = APP_ADV_DURATION;

  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);
}



static void ble_evt_handler(ble_evt_t const * p_ble_evt, void * p_context)                                                    //BLE Event handler
{
  ret_code_t err_code = NRF_SUCCESS;

  switch(p_ble_evt->header.evt_id)
  {
    case BLE_GAP_EVT_DISCONNECTED:                                                // Device disconnected event
    NRF_LOG_INFO("Device is disconnected!!!");

    break;

    case BLE_GAP_EVT_CONNECTED:                                                   // Device connected event
    NRF_LOG_INFO("Device is connected!!!");

    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:                                      // PHY update request event                            
    NRF_LOG_DEBUG("PHY Update Request.");

    ble_gap_phys_t const phys = 
    {
      .rx_phys = BLE_GAP_PHY_1MBPS,
      .tx_phys = BLE_GAP_PHY_1MBPS,
    };

    err_code = sd_ble_gap_phy_update(p_ble_evt->evt.gap_evt.conn_handle, &phys);
    APP_ERROR_CHECK(err_code);

    break;

  }
}



static void ble_stack_init(void)                                                                        //Initialize BLE stack
{
  ret_code_t err_code;

  err_code = nrf_sdh_enable_request();
  APP_ERROR_CHECK(err_code);

  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);

  err_code = nrf_sdh_ble_enable(&ram_start);
  APP_ERROR_CHECK(err_code);

  NRF_SDH_BLE_OBSERVER(m_ble_observer, APP_BLE_OBSERVER_PRIO, ble_evt_handler, NULL);


}


static void gpio_init(void)                                                                             //Initialize LEDS
{
  //nrf_gpio_cfg_output(sensor_en);
  //nrf_gpio_pin_set(sensor_en);
  nrf_delay_ms(100);
}



static void timers_init(void)                                                                           //Initialize app timer
{
  ret_code_t err_code = app_timer_init();
  APP_ERROR_CHECK(err_code);
}


static void log_init(void)                                                                                //Initialize the logger
{
  ret_code_t err_code = NRF_LOG_INIT(NULL);
  APP_ERROR_CHECK(err_code);

  NRF_LOG_DEFAULT_BACKENDS_INIT();

}


static void advertising_start(void)                                                                   //Start the advertisement
{
  ret_code_t err_code = ble_advertising_start(&m_advertising, BLE_ADV_MODE_FAST);

  APP_ERROR_CHECK(err_code);
}


static void idle_state_handle(void)
{
    if (NRF_LOG_PROCESS() == false)
    {
        nrf_pwr_mgmt_run();
    }
}


int main(void)
{

    //printf("Data sending\r\n");

    // Enter main loop.

    nrf_gpio_cfg_output(led);

    gpio_init();
    ble_stack_init();
    gap_params_init();
    //gatt_init();
    advertising_init();
    services_init();
    conn_params_init();
    advertising_start();
    nrf_delay_ms(100);


    for (;;)
    {
      
      //__WFE();      // Enter System ON sleep mode
      //__SEV();
      //__WFE();
      idle_state_handle();

       
    }
}



 

Please note that this code works perfectly with NRF52832 devices.

What will be the reason for this matter?

Your kind support and suggestions on this are highly appreciated.

Thanks in advance.

Parents
  • Hello Bhanuka,
    there are many reasons for why you might be troubleshooting custom HW. So let's check some of the typical steps and see:
    1. How did you do the programming, did you get a successful feedback when programming the device and can you read back the some content from the device after? 
    2. Is the voltage to the nRF_VDD actually what you think they are? Have you measured them?
    3. Is the program running in other aspects, toggling GPIOs or check the program counter for the device in debug mode if possible?
    4. Is the 32MHz crystal starting up for the BLE transmission? Can you measure the oscillation on the XC1 pin to see if it runs at any point?
    Best regards
    Asbjørn
Reply
  • Hello Bhanuka,
    there are many reasons for why you might be troubleshooting custom HW. So let's check some of the typical steps and see:
    1. How did you do the programming, did you get a successful feedback when programming the device and can you read back the some content from the device after? 
    2. Is the voltage to the nRF_VDD actually what you think they are? Have you measured them?
    3. Is the program running in other aspects, toggling GPIOs or check the program counter for the device in debug mode if possible?
    4. Is the 32MHz crystal starting up for the BLE transmission? Can you measure the oscillation on the XC1 pin to see if it runs at any point?
    Best regards
    Asbjørn
Children
No Data
Related