1bcf00d8fSMatthias Ringwald /*
2bcf00d8fSMatthias Ringwald * Copyright (C) 2014 BlueKitchen GmbH
3bcf00d8fSMatthias Ringwald *
4bcf00d8fSMatthias Ringwald * Redistribution and use in source and binary forms, with or without
5bcf00d8fSMatthias Ringwald * modification, are permitted provided that the following conditions
6bcf00d8fSMatthias Ringwald * are met:
7bcf00d8fSMatthias Ringwald *
8bcf00d8fSMatthias Ringwald * 1. Redistributions of source code must retain the above copyright
9bcf00d8fSMatthias Ringwald * notice, this list of conditions and the following disclaimer.
10bcf00d8fSMatthias Ringwald * 2. Redistributions in binary form must reproduce the above copyright
11bcf00d8fSMatthias Ringwald * notice, this list of conditions and the following disclaimer in the
12bcf00d8fSMatthias Ringwald * documentation and/or other materials provided with the distribution.
13bcf00d8fSMatthias Ringwald * 3. Neither the name of the copyright holders nor the names of
14bcf00d8fSMatthias Ringwald * contributors may be used to endorse or promote products derived
15bcf00d8fSMatthias Ringwald * from this software without specific prior written permission.
16bcf00d8fSMatthias Ringwald * 4. Any redistribution, use, or modification is done solely for
17bcf00d8fSMatthias Ringwald * personal benefit and not for any commercial purpose or for
18bcf00d8fSMatthias Ringwald * monetary gain.
19bcf00d8fSMatthias Ringwald *
20bcf00d8fSMatthias Ringwald * THIS SOFTWARE IS PROVIDED BY BLUEKITCHEN GMBH AND CONTRIBUTORS
21bcf00d8fSMatthias Ringwald * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22bcf00d8fSMatthias Ringwald * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
232fca4dadSMilanka Ringwald * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL BLUEKITCHEN
242fca4dadSMilanka Ringwald * GMBH OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
25bcf00d8fSMatthias Ringwald * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
26bcf00d8fSMatthias Ringwald * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
27bcf00d8fSMatthias Ringwald * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
28bcf00d8fSMatthias Ringwald * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
29bcf00d8fSMatthias Ringwald * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
30bcf00d8fSMatthias Ringwald * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31bcf00d8fSMatthias Ringwald * SUCH DAMAGE.
32bcf00d8fSMatthias Ringwald *
33bcf00d8fSMatthias Ringwald * Please inquire about commercial licensing options at
34bcf00d8fSMatthias Ringwald * [email protected]
35bcf00d8fSMatthias Ringwald *
36bcf00d8fSMatthias Ringwald */
37bcf00d8fSMatthias Ringwald
38e501bae0SMatthias Ringwald #define BTSTACK_FILE__ "gatt_battery_query.c"
39ab2c6ae4SMatthias Ringwald
40bcf00d8fSMatthias Ringwald // *****************************************************************************
414c517414SMilanka Ringwald /* EXAMPLE_START(gatt_battery_query): GATT Battery Service Client
42ec8ae085SMilanka Ringwald *
434c517414SMilanka Ringwald * @text This example demonstrates how to use the GATT Battery Service client to
444c517414SMilanka Ringwald * receive battery level information. The client supports querying of multiple
454c517414SMilanka Ringwald * battery services instances of on the remote device.
464c517414SMilanka Ringwald * The example scans for remote devices and connects to the first found device
474c517414SMilanka Ringwald * and starts the battery service client.
48ec8ae085SMilanka Ringwald */
494c517414SMilanka Ringwald // *****************************************************************************
50bcf00d8fSMatthias Ringwald
51bcf00d8fSMatthias Ringwald #include <stdint.h>
52bcf00d8fSMatthias Ringwald #include <stdio.h>
53bcf00d8fSMatthias Ringwald #include <stdlib.h>
54bcf00d8fSMatthias Ringwald #include <string.h>
55bcf00d8fSMatthias Ringwald
56bcf00d8fSMatthias Ringwald #include "btstack.h"
57a63a688aSMatthias Ringwald
58a63a688aSMatthias Ringwald // gatt_battery_query.gatt contains the declaration of the provided GATT Services + Characteristics
59a63a688aSMatthias Ringwald // gatt_battery_query.h contains the binary representation of gatt_battery_query.gatt
60a63a688aSMatthias Ringwald // it is generated by the build system by calling: $BTSTACK_ROOT/tool/compile_gatt.py gatt_battery_query.gatt gatt_battery_query.h
61a63a688aSMatthias Ringwald // it needs to be regenerated when the GATT Database declared in gatt_battery_query.gatt file is modified
62add9769eSMatthias Ringwald #include "gatt_battery_query.h"
63bcf00d8fSMatthias Ringwald
64bcf00d8fSMatthias Ringwald typedef struct advertising_report {
65bcf00d8fSMatthias Ringwald uint8_t type;
66bcf00d8fSMatthias Ringwald uint8_t event_type;
67bcf00d8fSMatthias Ringwald uint8_t address_type;
68bcf00d8fSMatthias Ringwald bd_addr_t address;
69bcf00d8fSMatthias Ringwald uint8_t rssi;
70bcf00d8fSMatthias Ringwald uint8_t length;
713ee82ab1SMilanka Ringwald const uint8_t * data;
72bcf00d8fSMatthias Ringwald } advertising_report_t;
73bcf00d8fSMatthias Ringwald
7483b6788cSMilanka Ringwald static enum {
7583b6788cSMilanka Ringwald APP_STATE_IDLE,
7683b6788cSMilanka Ringwald APP_STATE_W4_SCAN_RESULT,
7783b6788cSMilanka Ringwald APP_STATE_W4_CONNECT,
7883b6788cSMilanka Ringwald APP_STATE_CONNECTED
7983b6788cSMilanka Ringwald } app_state;
80bcf00d8fSMatthias Ringwald
810f09bd96SMilanka Ringwald static int blacklist_index = 0;
820f09bd96SMilanka Ringwald static bd_addr_t blacklist[20];
830f09bd96SMilanka Ringwald static advertising_report_t report;
840f09bd96SMilanka Ringwald
8583b6788cSMilanka Ringwald static hci_con_handle_t connection_handle;
8683b6788cSMilanka Ringwald static uint16_t battery_service_cid;
87bcf00d8fSMatthias Ringwald
88c30af2ffSMatthias Ringwald static bd_addr_t cmdline_addr;
89bcf00d8fSMatthias Ringwald static int cmdline_addr_found = 0;
90bcf00d8fSMatthias Ringwald
91bcf00d8fSMatthias Ringwald static btstack_packet_callback_registration_t hci_event_callback_registration;
92bcf00d8fSMatthias Ringwald
934c517414SMilanka Ringwald /* @section Main Application Setup
944c517414SMilanka Ringwald *
954c517414SMilanka Ringwald * @text The Listing MainConfiguration shows how to setup Battery Service client.
964c517414SMilanka Ringwald * Besides calling init() method for each service, you'll also need to register HCI packet handler
974c517414SMilanka Ringwald * to handle advertisements, as well as connect and disconect events.
984c517414SMilanka Ringwald *
994c517414SMilanka Ringwald * @text Handling of GATT Battery Service events will be later delegated to a sepparate packet
1004c517414SMilanka Ringwald * handler, i.e. gatt_client_event_handler.
1014c517414SMilanka Ringwald *
1024c517414SMilanka Ringwald * @note There are two additional files associated with this client to allow a remote device to query out GATT database:
1034c517414SMilanka Ringwald * - gatt_battary_query.gatt - contains the declaration of the provided GATT Services and Characteristics.
1044c517414SMilanka Ringwald * - gatt_battary_query.h - contains the binary representation of gatt_battary_query.gatt.
1054c517414SMilanka Ringwald *
1064c517414SMilanka Ringwald * gatt_battary_query.h is generated by the build system by calling:
1074c517414SMilanka Ringwald * $BTSTACK_ROOT/tool/compile_gatt.py gatt_battary_query.gatt gatt_battary_query.h
1084c517414SMilanka Ringwald * This file needs to be regenerated when the GATT Database declared in gatt_battary_query.gatt file is modified.
1094c517414SMilanka Ringwald */
1104c517414SMilanka Ringwald
1114c517414SMilanka Ringwald /* LISTING_START(MainConfiguration): Setup Device Battery Client service */
1124c517414SMilanka Ringwald static void hci_event_handler(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size);
1134c517414SMilanka Ringwald static void gatt_client_event_handler(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size);
1144c517414SMilanka Ringwald
battery_service_client_setup(void)1154c517414SMilanka Ringwald static void battery_service_client_setup(void){
1164c517414SMilanka Ringwald // Init L2CAP
1174c517414SMilanka Ringwald l2cap_init();
1184c517414SMilanka Ringwald
1194c517414SMilanka Ringwald // Setup ATT server - only needed if LE Peripheral does ATT queries on its own, e.g. Android phones
1204c517414SMilanka Ringwald att_server_init(profile_data, NULL, NULL);
1214c517414SMilanka Ringwald
1224c517414SMilanka Ringwald // GATT Client setup
1234c517414SMilanka Ringwald gatt_client_init();
1244c517414SMilanka Ringwald // Device Information Service Client setup
1254c517414SMilanka Ringwald battery_service_client_init();
1264c517414SMilanka Ringwald
1274c517414SMilanka Ringwald sm_init();
1284c517414SMilanka Ringwald sm_set_io_capabilities(IO_CAPABILITY_NO_INPUT_NO_OUTPUT);
1294c517414SMilanka Ringwald
1304c517414SMilanka Ringwald hci_event_callback_registration.callback = &hci_event_handler;
1314c517414SMilanka Ringwald hci_add_event_handler(&hci_event_callback_registration);
1324c517414SMilanka Ringwald }
1334c517414SMilanka Ringwald /* LISTING_END */
1344c517414SMilanka Ringwald
blacklist_size(void)135287eecffSMilanka Ringwald static int blacklist_size(void){
1360f09bd96SMilanka Ringwald return sizeof(blacklist) / sizeof(bd_addr_t);
1370f09bd96SMilanka Ringwald }
1380f09bd96SMilanka Ringwald
blacklist_contains(bd_addr_t addr)1390f09bd96SMilanka Ringwald static int blacklist_contains(bd_addr_t addr){
1400f09bd96SMilanka Ringwald int i;
1410f09bd96SMilanka Ringwald for (i=0; i<blacklist_size(); i++){
1420f09bd96SMilanka Ringwald if (bd_addr_cmp(addr, blacklist[i]) == 0) return 1;
1430f09bd96SMilanka Ringwald }
1440f09bd96SMilanka Ringwald return 0;
1450f09bd96SMilanka Ringwald }
1460f09bd96SMilanka Ringwald
add_to_blacklist(bd_addr_t addr)1470f09bd96SMilanka Ringwald static void add_to_blacklist(bd_addr_t addr){
14889b171cfSMilanka Ringwald printf("%s added to blacklist (no battery service found).\n", bd_addr_to_str(addr));
1490f09bd96SMilanka Ringwald bd_addr_copy(blacklist[blacklist_index], addr);
1500f09bd96SMilanka Ringwald blacklist_index = (blacklist_index + 1) % blacklist_size();
1510f09bd96SMilanka Ringwald }
1520f09bd96SMilanka Ringwald
dump_advertising_report(uint8_t * packet)15383b6788cSMilanka Ringwald static void dump_advertising_report(uint8_t *packet){
15483b6788cSMilanka Ringwald bd_addr_t address;
15583b6788cSMilanka Ringwald gap_event_advertising_report_get_address(packet, address);
15683b6788cSMilanka Ringwald
15783b6788cSMilanka Ringwald printf(" * adv. event: evt-type %u, addr-type %u, addr %s, rssi %u, length adv %u, data: ",
15883b6788cSMilanka Ringwald gap_event_advertising_report_get_advertising_event_type(packet),
15983b6788cSMilanka Ringwald gap_event_advertising_report_get_address_type(packet),
16083b6788cSMilanka Ringwald bd_addr_to_str(address),
16183b6788cSMilanka Ringwald gap_event_advertising_report_get_rssi(packet),
16283b6788cSMilanka Ringwald gap_event_advertising_report_get_data_length(packet));
16383b6788cSMilanka Ringwald printf_hexdump(gap_event_advertising_report_get_data(packet), gap_event_advertising_report_get_data_length(packet));
164bcf00d8fSMatthias Ringwald
165bcf00d8fSMatthias Ringwald }
166bcf00d8fSMatthias Ringwald
1674c517414SMilanka Ringwald /* LISTING_START(packetHandler): Packet Handler */
hci_event_handler(uint8_t packet_type,uint16_t channel,uint8_t * packet,uint16_t size)1684c517414SMilanka Ringwald static void hci_event_handler(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size){
1694c517414SMilanka Ringwald /* LISTING_PAUSE */
1704c517414SMilanka Ringwald UNUSED(channel);
1714c517414SMilanka Ringwald UNUSED(size);
1724c517414SMilanka Ringwald
1734c517414SMilanka Ringwald /* LISTING_RESUME */
1744c517414SMilanka Ringwald
1754c517414SMilanka Ringwald if (packet_type != HCI_EVENT_PACKET){
1764c517414SMilanka Ringwald return;
1774c517414SMilanka Ringwald }
1784c517414SMilanka Ringwald
1794c517414SMilanka Ringwald switch (hci_event_packet_get_type(packet)) {
1804c517414SMilanka Ringwald /* LISTING_PAUSE */
1814c517414SMilanka Ringwald
1824c517414SMilanka Ringwald case BTSTACK_EVENT_STATE:
1834c517414SMilanka Ringwald // BTstack activated, get started
1844c517414SMilanka Ringwald if (btstack_event_state_get_state(packet) != HCI_STATE_WORKING) break;
1854c517414SMilanka Ringwald if (cmdline_addr_found){
1864c517414SMilanka Ringwald printf("Connect to %s\n", bd_addr_to_str(cmdline_addr));
1874c517414SMilanka Ringwald app_state = APP_STATE_W4_CONNECT;
1884c517414SMilanka Ringwald gap_connect(cmdline_addr, 0);
1894c517414SMilanka Ringwald break;
1904c517414SMilanka Ringwald }
1914c517414SMilanka Ringwald printf("Start scanning!\n");
1924c517414SMilanka Ringwald app_state = APP_STATE_W4_SCAN_RESULT;
1934c517414SMilanka Ringwald gap_set_scan_parameters(0,0x0030, 0x0030);
1944c517414SMilanka Ringwald gap_start_scan();
1954c517414SMilanka Ringwald break;
1964c517414SMilanka Ringwald
1974c517414SMilanka Ringwald case GAP_EVENT_ADVERTISING_REPORT:
1984c517414SMilanka Ringwald if (app_state != APP_STATE_W4_SCAN_RESULT) return;
1994c517414SMilanka Ringwald
200a220ab31SMatthias Ringwald gap_event_advertising_report_get_address(packet, report.address);
201a220ab31SMatthias Ringwald report.address_type = gap_event_advertising_report_get_address_type(packet);
202a220ab31SMatthias Ringwald if (blacklist_contains(report.address)) {
2034c517414SMilanka Ringwald break;
2044c517414SMilanka Ringwald }
2054c517414SMilanka Ringwald dump_advertising_report(packet);
2064c517414SMilanka Ringwald
2074c517414SMilanka Ringwald // stop scanning, and connect to the device
2084c517414SMilanka Ringwald app_state = APP_STATE_W4_CONNECT;
2094c517414SMilanka Ringwald gap_stop_scan();
2104c517414SMilanka Ringwald printf("Stop scan. Connect to device with addr %s.\n", bd_addr_to_str(report.address));
2114c517414SMilanka Ringwald gap_connect(report.address,report.address_type);
2124c517414SMilanka Ringwald break;
2134c517414SMilanka Ringwald
2144c517414SMilanka Ringwald /* LISTING_RESUME */
215bba48196SMatthias Ringwald case HCI_EVENT_META_GAP:
2164c517414SMilanka Ringwald // Wait for connection complete
217bba48196SMatthias Ringwald if (hci_event_gap_meta_get_subevent_code(packet) != GAP_SUBEVENT_LE_CONNECTION_COMPLETE) break;
2184c517414SMilanka Ringwald
2194c517414SMilanka Ringwald /* LISTING_PAUSE */
2204c517414SMilanka Ringwald if (app_state != APP_STATE_W4_CONNECT) return;
2214c517414SMilanka Ringwald
2224c517414SMilanka Ringwald /* LISTING_RESUME */
2234c517414SMilanka Ringwald // Get connection handle from event
224bba48196SMatthias Ringwald connection_handle = gap_subevent_le_connection_complete_get_connection_handle(packet);
2254c517414SMilanka Ringwald
2264c517414SMilanka Ringwald // Connect to remote Battery Service.
2274c517414SMilanka Ringwald // On succesful connection, the client tries to register for notifications. If notifications
2284c517414SMilanka Ringwald // are not supported by remote Battery Service, the client will automatically poll the battery level - here every 2 seconds.
2294c517414SMilanka Ringwald // If poll_interval_ms is 0, polling is disabled, and only notifications will be received (for manual polling,
2304c517414SMilanka Ringwald // see battery_service_client.h).
2314c517414SMilanka Ringwald // All GATT Battery Service events are handled by the gatt_client_event_handler.
23279e58675SMatthias Ringwald (void) battery_service_client_connect(connection_handle, gatt_client_event_handler, 2000, &battery_service_cid);
2334c517414SMilanka Ringwald
2344c517414SMilanka Ringwald app_state = APP_STATE_CONNECTED;
2354c517414SMilanka Ringwald printf("Battery service connected.\n");
2364c517414SMilanka Ringwald break;
2374c517414SMilanka Ringwald
2384c517414SMilanka Ringwald case HCI_EVENT_DISCONNECTION_COMPLETE:
2394c517414SMilanka Ringwald connection_handle = HCI_CON_HANDLE_INVALID;
2404c517414SMilanka Ringwald // Disconnect battery service
2414c517414SMilanka Ringwald battery_service_client_disconnect(battery_service_cid);
2424c517414SMilanka Ringwald
2434c517414SMilanka Ringwald /* LISTING_PAUSE */
2444c517414SMilanka Ringwald if (cmdline_addr_found){
2454c517414SMilanka Ringwald printf("Disconnected %s\n", bd_addr_to_str(cmdline_addr));
2464c517414SMilanka Ringwald return;
2474c517414SMilanka Ringwald }
2484c517414SMilanka Ringwald
2494c517414SMilanka Ringwald /* LISTING_RESUME */
2504c517414SMilanka Ringwald printf("Disconnected %s\n", bd_addr_to_str(report.address));
2514c517414SMilanka Ringwald printf("Restart scan.\n");
2524c517414SMilanka Ringwald app_state = APP_STATE_W4_SCAN_RESULT;
2534c517414SMilanka Ringwald gap_start_scan();
2544c517414SMilanka Ringwald break;
2554c517414SMilanka Ringwald default:
2564c517414SMilanka Ringwald break;
2574c517414SMilanka Ringwald }
2584c517414SMilanka Ringwald }
2594c517414SMilanka Ringwald /* LISTING_END */
2604c517414SMilanka Ringwald
2614c517414SMilanka Ringwald /* LISTING_START(gatt_client_event_handler): GATT Client Event Handler */
2624c517414SMilanka Ringwald // The gatt_client_event_handler receives following events from remote device:
2634c517414SMilanka Ringwald // - GATTSERVICE_SUBEVENT_BATTERY_SERVICE_CONNECTED
2644c517414SMilanka Ringwald // - GATTSERVICE_SUBEVENT_BATTERY_SERVICE_LEVEL
2654c517414SMilanka Ringwald //
gatt_client_event_handler(uint8_t packet_type,uint16_t channel,uint8_t * packet,uint16_t size)2664c517414SMilanka Ringwald static void gatt_client_event_handler(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size){
2674c517414SMilanka Ringwald /* LISTING_PAUSE */
2689ec2630cSMatthias Ringwald UNUSED(packet_type);
2699ec2630cSMatthias Ringwald UNUSED(channel);
2709ec2630cSMatthias Ringwald UNUSED(size);
2719ec2630cSMatthias Ringwald
2724c517414SMilanka Ringwald /* LISTING_RESUME */
273f3d85318SMilanka Ringwald uint8_t status;
274f3d85318SMilanka Ringwald uint8_t att_status;
275bcf00d8fSMatthias Ringwald
276174a0c1cSMilanka Ringwald if (hci_event_packet_get_type(packet) != HCI_EVENT_GATTSERVICE_META){
277174a0c1cSMilanka Ringwald return;
278174a0c1cSMilanka Ringwald }
279174a0c1cSMilanka Ringwald
280174a0c1cSMilanka Ringwald switch (hci_event_gattservice_meta_get_subevent_code(packet)){
2817ec9a1bbSMilanka Ringwald case GATTSERVICE_SUBEVENT_BATTERY_SERVICE_CONNECTED:
2827ec9a1bbSMilanka Ringwald status = gattservice_subevent_battery_service_connected_get_status(packet);
283174a0c1cSMilanka Ringwald switch (status){
284174a0c1cSMilanka Ringwald case ERROR_CODE_SUCCESS:
285f3d85318SMilanka Ringwald printf("Battery service client connected, found %d services, poll bitmap 0x%02x\n",
286f3d85318SMilanka Ringwald gattservice_subevent_battery_service_connected_get_num_instances(packet),
287f3d85318SMilanka Ringwald gattservice_subevent_battery_service_connected_get_poll_bitmap(packet));
2888dbd7793SMatthias Ringwald battery_service_client_read_battery_level(battery_service_cid, 0);
289bcf00d8fSMatthias Ringwald break;
290174a0c1cSMilanka Ringwald default:
291fcd55a0bSMilanka Ringwald printf("Battery service client connection failed, status 0x%02x.\n", status);
2920f09bd96SMilanka Ringwald add_to_blacklist(report.address);
2930f09bd96SMilanka Ringwald gap_disconnect(connection_handle);
294bcf00d8fSMatthias Ringwald break;
295bcf00d8fSMatthias Ringwald }
296bcf00d8fSMatthias Ringwald break;
297174a0c1cSMilanka Ringwald
29883b6788cSMilanka Ringwald case GATTSERVICE_SUBEVENT_BATTERY_SERVICE_LEVEL:
299f3d85318SMilanka Ringwald att_status = gattservice_subevent_battery_service_level_get_att_status(packet);
300f3d85318SMilanka Ringwald if (att_status != ATT_ERROR_SUCCESS){
301f3d85318SMilanka Ringwald printf("Battery level read failed, ATT Error 0x%02x\n", att_status);
302f3d85318SMilanka Ringwald } else {
30389b171cfSMilanka Ringwald printf("Service index: %d, Battery level: %d\n",
304*7b782c70SMatthias Ringwald gattservice_subevent_battery_service_level_get_service_index(packet),
30583b6788cSMilanka Ringwald gattservice_subevent_battery_service_level_get_level(packet));
306f3d85318SMilanka Ringwald
307f3d85318SMilanka Ringwald }
3080f09bd96SMilanka Ringwald break;
309bcf00d8fSMatthias Ringwald
310bcf00d8fSMatthias Ringwald default:
311bcf00d8fSMatthias Ringwald break;
312bcf00d8fSMatthias Ringwald }
313bcf00d8fSMatthias Ringwald }
3144c517414SMilanka Ringwald /* LISTING_END */
315bcf00d8fSMatthias Ringwald
316bcf00d8fSMatthias Ringwald int btstack_main(int argc, const char * argv[]);
btstack_main(int argc,const char * argv[])317bcf00d8fSMatthias Ringwald int btstack_main(int argc, const char * argv[]){
318bcf00d8fSMatthias Ringwald
31983b6788cSMilanka Ringwald // parse address if command line arguments are provided
3202e80d8ecSSteven Buytaert int arg;
321bcf00d8fSMatthias Ringwald cmdline_addr_found = 0;
322bcf00d8fSMatthias Ringwald
3232e80d8ecSSteven Buytaert for (arg = 1; arg < argc; arg++) {
324bcf00d8fSMatthias Ringwald if(!strcmp(argv[arg], "-a") || !strcmp(argv[arg], "--address")){
3252e80d8ecSSteven Buytaert if (arg + 1 < argc) {
326bcf00d8fSMatthias Ringwald arg++;
327a6efb919SMatthias Ringwald cmdline_addr_found = sscanf_bd_addr(argv[arg], cmdline_addr);
328bcf00d8fSMatthias Ringwald }
3292e80d8ecSSteven Buytaert if (!cmdline_addr_found) {
33083b6788cSMilanka Ringwald fprintf(stderr, "\nUsage: %s [-a|--address aa:bb:cc:dd:ee:ff]\n", argv[0]);
3312e80d8ecSSteven Buytaert fprintf(stderr, "If no argument is provided, %s will start scanning and connect to the first found device.\n"
3322e80d8ecSSteven Buytaert "To connect to a specific device use argument [-a].\n\n", argv[0]);
3332e80d8ecSSteven Buytaert return 1;
334bcf00d8fSMatthias Ringwald }
3352e80d8ecSSteven Buytaert }
3362e80d8ecSSteven Buytaert }
3372e80d8ecSSteven Buytaert if (!cmdline_addr_found) {
3382e80d8ecSSteven Buytaert fprintf(stderr, "No specific address specified or found; start scanning for any advertiser.\n");
3392e80d8ecSSteven Buytaert }
34083b6788cSMilanka Ringwald
3414c517414SMilanka Ringwald battery_service_client_setup();
342a4fe6467SMatthias Ringwald
34383b6788cSMilanka Ringwald app_state = APP_STATE_IDLE;
344a4fe6467SMatthias Ringwald
345bcf00d8fSMatthias Ringwald // turn on!
346bcf00d8fSMatthias Ringwald hci_power_control(HCI_POWER_ON);
347bcf00d8fSMatthias Ringwald
348bcf00d8fSMatthias Ringwald return 0;
349bcf00d8fSMatthias Ringwald }
350bcf00d8fSMatthias Ringwald
351ec8ae085SMilanka Ringwald /* EXAMPLE_END */
352bcf00d8fSMatthias Ringwald
353bcf00d8fSMatthias Ringwald
354