How can I add scan response data to the SDK example ble_app_beacon?
How can I add scan response data to the SDK example ble_app_beacon?
Hi!
The approach might vary depending on what version of the SDK you are working with.
Maybe you could provide a little more information?
SDK version, what device, softdevice version etc. is useful information to add in your questions.
However, you can take a look at our advertising tutorial, and the chapter about the Scan response data.
The tutorial is from one of the older SDK but the approach will be similiar.
Also, the ble_app_uart example adds data to the scan reponse packet, so you can get an idea of how it's done.
Let me know if you have any further questions.
Best regards,
Joakim.
I have looked into the ble_app_uart example, but I cannot find the line(s) where the scan response data is set.
I receive
Advertisement data: 02:01:05:0C:09:4E:6F:72:64:69:63:5F:55:41:52:54 (here at the end is Nordic_UART)
Scan response data: 11:07:9E:CA:DC:24:0E:E5:A9:E0:93:F3:A3:B5:01:00:40:6E
But where is the scan response data in the code?
Thanks for your help!
Hi Joakim,
I was looking how to program:
- iBeacon (to be recognized by iOS)
- with scan response data (for additional measurement or other data)
- and connectable (to act as normal BLE peripheral)
I succeeded (after combining your info and single stepping through some code)
Here is my example:
static void advertising_init(void) { uint32_t err_code; uint8_t index; uint8_t ch_array[10]; uint16_t major_value; uint16_t minor_value; ble_advdata_t advdata; ble_advdata_t srdata; ble_advdata_manuf_data_t manuf_specific_data; ble_advdata_service_data_t service_data_array; //Compose iBeacon data. Put the measurement data as major_value and minor_value manuf_specific_data.company_identifier = APP_COMPANY_IDENTIFIER; //Apple iBeacon. Others are not recognized by iOS index = MAJ_VAL_OFFSET_IN_BEACON_INFO; m_beacon_info[index++] = 0xab;//MSB_16(major_value); m_beacon_info[index++] = 0xcd;//LSB_16(major_value); m_beacon_info[index++] = 0xef;//MSB_16(minor_value); m_beacon_info[index++] = MyTime; //LSB_16(minor_value); manuf_specific_data.data.p_data = (uint8_t *) m_beacon_info; manuf_specific_data.data.size = APP_BEACON_INFO_LENGTH; // Build and set advertising data: flags, manufacturer_specific_data memset(&advdata, 0, sizeof(advdata)); advdata.name_type = BLE_ADVDATA_NO_NAME; //name will be included in scan response data advdata.flags = BLE_GAP_ADV_FLAGS_LE_ONLY_GENERAL_DISC_MODE; advdata.p_manuf_specific_data = &manuf_specific_data; // Build and set scan response data: name, service_data memset(&srdata, 0, sizeof(srdata)); srdata.name_type = BLE_ADVDATA_SHORT_NAME; srdata.short_name_len = 3; // Advertise only first 3 letters of name ch_array[0] = 0; //eight interesting bytes ch_array[1] = 1; ch_array[2] = 2; ch_array[3] = 3; ch_array[4] = 4; ch_array[5] = 5; ch_array[6] = 6; ch_array[7] = 7; service_data_array.service_uuid = 0x5678; //16 bit UUID still TBD service_data_array.data.size = 8; service_data_array.data.p_data = ch_array; srdata.service_data_count = 1; srdata.p_service_data_array = &service_data_array; // Initialize advertising parameters (used when starting advertising). memset(&m_adv_params, 0, sizeof(m_adv_params)); m_adv_params.properties.type = BLE_GAP_ADV_TYPE_CONNECTABLE_SCANNABLE_UNDIRECTED; m_adv_params.p_peer_addr = NULL; // Undirected advertisement. m_adv_params.filter_policy = BLE_GAP_ADV_FP_ANY; m_adv_params.interval = NON_CONNECTABLE_ADV_INTERVAL; m_adv_params.duration = 0; // Never time out. m_adv_params.primary_phy = BLE_GAP_PHY_1MBPS; m_adv_params.duration = APP_ADV_DURATION; m_adv_params.interval = APP_ADV_INTERVAL; //First encode the advertisement data err_code = ble_advdata_encode(&advdata, m_adv_data.adv_data.p_data, &m_adv_data.adv_data.len); APP_ERROR_CHECK(err_code); //Now encode the scan response data err_code = ble_advdata_encode(&srdata, m_adv_data.scan_rsp_data.p_data, &m_adv_data.scan_rsp_data.len); APP_ERROR_CHECK(err_code); err_code = sd_ble_gap_adv_set_configure(&m_adv_handle, &m_adv_data, &m_adv_params); APP_ERROR_CHECK(err_code); nrf_gpio_pin_toggle(NRF_GPIO_PIN_MAP(0, 30)); }
Now my advertisement data is:
02:01:06:1A:FF:59:00:02:15:01:12:23:34:45:56:67:78:89:9A:AB:BC:CD:DE:EF:F0:AB:CD:EF:00:C3
And the scna response data is:
0B:16:78:56:00:01:02:03:04:05:06:07:04:08:45:50:50
I hope it can help other programmers.
Best regards,
Wim
I forgot a few lines of code:
#define APP_BEACON_INFO_LENGTH 0x17 /**< Total length of information advertised by the Beacon. */ #define APP_ADV_DATA_LENGTH 0x15 /**< Length of manufacturer specific data in the advertisement. */ #define APP_DEVICE_TYPE 0x02 /**< 0x02 refers to Beacon. */ #define APP_MEASURED_RSSI 0xC3 /**< The Beacon's measured RSSI at 1 meter distance in dBm. */ #define APP_COMPANY_IDENTIFIER 0x0059 /**< Company identifier for Nordic Semiconductor ASA. as per www.bluetooth.org. */ #define APP_MAJOR_VALUE 0x01, 0x02 /**< Major value used to identify Beacons. */ #define APP_MINOR_VALUE 0x03, 0x04 /**< Minor value used to identify Beacons. */ #define APP_BEACON_UUID 0x01, 0x12, 0x23, 0x34, \ 0x45, 0x56, 0x67, 0x78, \ 0x89, 0x9a, 0xab, 0xbc, \ 0xcd, 0xde, 0xef, 0xf0 /**< Proprietary UUID for Beacon. */ #define MAJ_VAL_OFFSET_IN_BEACON_INFO 18 /**< Position of the MSB of the Major Value in m_beacon_info array. */ static uint8_t m_beacon_info[APP_BEACON_INFO_LENGTH] = /**< Information advertised by the Beacon. */ { APP_DEVICE_TYPE, // Manufacturer specific information. Specifies the device type in this // implementation. APP_ADV_DATA_LENGTH, // Manufacturer specific information. Specifies the length of the // manufacturer specific data in this implementation. APP_BEACON_UUID, // 128 bit UUID value. APP_MAJOR_VALUE, // Major arbitrary value that can be used to distinguish between Beacons. APP_MINOR_VALUE, // Minor arbitrary value that can be used to distinguish between Beacons. APP_MEASURED_RSSI // Manufacturer specific information. The Beacon's measured TX power in // this implementation. };
Hi.
Thanks for sharing your solution, so that others might benefit from it.
Best regards,
Joakim.
Also do not forget to change these lines (if not yet done):
static ble_gap_adv_data_t m_adv_data = { .adv_data = { .p_data = m_enc_advdata, .len = BLE_GAP_ADV_SET_DATA_SIZE_MAX }, .scan_rsp_data = { .p_data = m_enc_scan_response_data, //was NULL, .len = BLE_GAP_ADV_SET_DATA_SIZE_MAX // was 0 } };
In this code when it says m_enc_scan_response_data is undeclared.
If possible can you please share your main.c file, would greatly help indeed.
In this code when it says m_enc_scan_response_data is undeclared.
If possible can you please share your main.c file, would greatly help indeed.
Added m_enc_scan_response_data by:
static uint8_t m_enc_scan_response_data[BLE_GAP_ADV_SET_DATA_SIZE_MAX];
#define APP_ADV_INTERVAL 64 /**< The advertising interval (in units of 0.625 ms. This value corresponds to 40 ms). */ #define APP_ADV_DURATION 18000
err_code = sd_ble_gap_adv_start(m_adv_handle, APP_BLE_CONN_CFG_TAG); APP_ERROR_CHECK(err_code);
err_code = nrf_sdh_ble_enable(&ram_start); APP_ERROR_CHECK(err_code);