Hackster is hosting Hackster Holidays, Ep. 7: Livestream & Giveaway Drawing. Watch previous episodes or stream live on Friday!Stream Hackster Holidays, Ep. 7 on Friday!
DongEun Koak (kaizen)
Published © Apache-2.0

BLE to Ethernet Thin Gateway

BLE to Ethernet Thin Gateway is the data collector to transmit the BLE (Bluetooth Low Energy) data to a cloud server through Ethernet.

IntermediateFull instructions provided3,685
BLE to Ethernet Thin Gateway

Things used in this project

Hardware components

W5500
WIZnet W5500
×1

Story

Read more

Code

Code snippet #1

Plain text
ble_app_hrs : <SDK>/examples/ble_peripheral
ble_app_hrs_c_with_W5500 : <SDK>/examples/ble_central

Code snippet #2

Plain text
<SDK>/examples/ble_peripheral/ble_app_hrs/pca10028/s110/armgcc

Code snippet #3

Plain text
<SDK>/examples/ble_central/ble_app_hrs_c_with_W5500/pca10028/s120/armgcc

Code snippet #4

Plain text
APP_TIMER_DEF(m_publish_data_timer_id);
 
int main(void)
{
    bool erase_bonds;
    uint32_t err_code;
 
    // Initialize.
    APP_TIMER_INIT(APP_TIMER_PRESCALER, APP_TIMER_OP_QUEUE_SIZE, NULL);
 
    buttons_leds_init(&erase_bonds);
    uart_init();
    printf("Heart rate collector example\r\n");
 
    spi0_master_init();
    user_ethernet_init();
 
    app_mailbox_create(&hr_data_mailbox);
    app_mailbox_create(&bas_data_mailbox);
 
    ble_stack_init();
    device_manager_init(erase_bonds);
    db_discovery_init();
 
    hrs_c_init();
    bas_c_init();
 
 
    // Start scanning for peripherals and initiate connection
    // with devices that advertise Heart Rate UUID.
    scan_start();
 
    err_code = app_timer_create(&m_publish_data_timer_id, APP_TIMER_MODE_REPEATED, publish_data_handler);
    APP_ERROR_CHECK(err_code);
    err_code = app_timer_start(m_publish_data_timer_id,PUBLISH_INTERVAL,NULL);
    APP_ERROR_CHECK(err_code);
 
 
    for (;; )
    {
    	power_manage();
    }
}

Code snippet #5

Plain text
#define HR_EVT_MAILBOX_QUEUE_SIZE     10
#define BAS_EVT_MAILBOX_QUEUE_SIZE    10
 
typedef struct
{
    uint16_t evt_data;
    uint16_t dummy_data;
}hrs_c_evt_data;
 
typedef struct
{
    uint16_t battery_level;
    uint16_t dummy_data;
}bas_c_evt_data;
 
APP_MAILBOX_DEF(hr_data_mailbox, HR_EVT_MAILBOX_QUEUE_SIZE, sizeof(hrs_c_evt_data));
APP_MAILBOX_DEF(bas_data_mailbox, BAS_EVT_MAILBOX_QUEUE_SIZE, sizeof(bas_c_evt_data));
 
static any_port = 50000;
uint8_t dweet_io_ip[4] = {54,172,56,193};
uint16_t dest_port = 80;
#define THING         "Ble2Eth"
#define HEART_RATE     "heart_rate"
#define BATTERY     "battery"

Code snippet #6

Plain text
static void publish_data_handler(void * p_context)
{
    UNUSED_PARAMETER(p_context);
    uint8_t sn = 0;
    uint32_t ret;
    uint8_t eth_data[512];
    hrs_c_evt_data hr_data;
    bas_c_evt_data batt_data;
 
    // Connect to server
    if(app_mailbox_length_get(&hr_data_mailbox) || app_mailbox_length_get(&bas_data_mailbox))
    {
        if(getSn_SR(sn) != SOCK_CLOSED)
        {
            close(sn);
            disconnect(sn);
        }
        while(getSn_SR(sn) != SOCK_CLOSED);
 
        if( ret = socket(sn, Sn_MR_TCP, any_port++, 0x00) != sn )
        {
            APPL_LOG("[PUBLISH]: Socket open failed, reason %d\r\n", ret);
            return;
        }
 
        if( ret = connect(sn, dweet_io_ip, dest_port) != SOCK_OK )
        {
            APPL_LOG("[PUBLISH]: Socket Connection failed, reason %d\r\n", ret);
            return;
        }
    }
    else    return;
 
    // Publish collected data
    while( app_mailbox_length_get(&hr_data_mailbox) != 0)
    {
        app_mailbox_get(&hr_data_mailbox,&hr_data);
        sprintf(eth_data,"GET /dweet/for/%s?%s=%d HTTP/1.1\r\nHost: dweet. io\r\n\r\n",THING,HEART_RATE,hr_data.evt_data);
        send(sn,eth_data,strlen((uint8_t*)eth_data));
    }
 
    while( app_mailbox_length_get(&bas_data_mailbox) != 0)
    {
        app_mailbox_get(&bas_data_mailbox,&batt_data);
        sprintf(eth_data,"GET /dweet/for/%s?%s=%d HTTP/1.1\r\nHost: dweet. io\r\n\r\n",THING,BATTERY,batt_data.battery_level);
        send(sn,eth_data,strlen((uint8_t*)eth_data));
    }
 
    close(sn);
    disconnect(sn);
}

Code snippet #7

Plain text
/**@brief Heart Rate Collector Handler.
 */
static void hrs_c_evt_handler(ble_hrs_c_t * p_hrs_c, ble_hrs_c_evt_t * p_hrs_c_evt)
{
    uint32_t err_code;
    uint32_t test;
    hrs_c_evt_data hrs_c_data;
 
    switch (p_hrs_c_evt->evt_type)
    {
        case BLE_HRS_C_EVT_DISCOVERY_COMPLETE:
 
            // Heart rate service discovered. Enable notification of Heart Rate Measurement.
            err_code = ble_hrs_c_hrm_notif_enable(p_hrs_c);
            APP_ERROR_CHECK(err_code);
 
            printf("Heart rate service discovered \r\n");
            break;
 
        case BLE_HRS_C_EVT_HRM_NOTIFICATION:
        {
            APPL_LOG("[APPL]: HR Measurement received %d \r\n", p_hrs_c_evt->params.hrm.hr_value);
            hrs_c_data.evt_data = p_hrs_c_evt->params.hrm.hr_value;
            app_mailbox_put(&hr_data_mailbox,&hrs_c_data);
            break;
        }
 
        default:
            break;
    }
}
 
 
/**@brief Battery levelCollector Handler.
 */
static void bas_c_evt_handler(ble_bas_c_t * p_bas_c, ble_bas_c_evt_t * p_bas_c_evt)
{
    uint32_t err_code;
    bas_c_evt_data bas_data;
 
    switch (p_bas_c_evt->evt_type)
    {
        case BLE_BAS_C_EVT_DISCOVERY_COMPLETE:
            // Batttery service discovered. Enable notification of Battery Level.
            APPL_LOG("[APPL]: Battery Service discovered. \r\n");
 
            APPL_LOG("[APPL]: Reading battery level. \r\n");
 
            err_code = ble_bas_c_bl_read(p_bas_c);
            APP_ERROR_CHECK(err_code);
 
 
            APPL_LOG("[APPL]: Enabling Battery Level Notification. \r\n");
            err_code = ble_bas_c_bl_notif_enable(p_bas_c);
            APP_ERROR_CHECK(err_code);
 
            break;
 
        case BLE_BAS_C_EVT_BATT_NOTIFICATION:
        {
            APPL_LOG("[APPL]: Battery Level received %d %%\r\n", p_bas_c_evt->params.battery_level);
            bas_data.battery_level = p_bas_c_evt->params.battery_level;
            app_mailbox_put(&bas_data_mailbox,&bas_data);
            break;
        }
 
        case BLE_BAS_C_EVT_BATT_READ_RESP:
        {
            APPL_LOG("[APPL]: Battery Level Read as %d %%\r\n", p_bas_c_evt->params.battery_level);
            break;
        }
 
        default:
            break;
    }
}

Github

https://github.com/kaizen8501/nRF51_SDK_10.0.0_Example

Credits

DongEun Koak (kaizen)
6 projects • 8 followers

Comments