xref: /btstack/port/posix-h4/main.c (revision 5b67487b548c753e40bdc13d8cb5bf9319c90c3c)
18caefee3SMatthias Ringwald /*
28caefee3SMatthias Ringwald  * Copyright (C) 2014 BlueKitchen GmbH
38caefee3SMatthias Ringwald  *
48caefee3SMatthias Ringwald  * Redistribution and use in source and binary forms, with or without
58caefee3SMatthias Ringwald  * modification, are permitted provided that the following conditions
68caefee3SMatthias Ringwald  * are met:
78caefee3SMatthias Ringwald  *
88caefee3SMatthias Ringwald  * 1. Redistributions of source code must retain the above copyright
98caefee3SMatthias Ringwald  *    notice, this list of conditions and the following disclaimer.
108caefee3SMatthias Ringwald  * 2. Redistributions in binary form must reproduce the above copyright
118caefee3SMatthias Ringwald  *    notice, this list of conditions and the following disclaimer in the
128caefee3SMatthias Ringwald  *    documentation and/or other materials provided with the distribution.
138caefee3SMatthias Ringwald  * 3. Neither the name of the copyright holders nor the names of
148caefee3SMatthias Ringwald  *    contributors may be used to endorse or promote products derived
158caefee3SMatthias Ringwald  *    from this software without specific prior written permission.
168caefee3SMatthias Ringwald  * 4. Any redistribution, use, or modification is done solely for
178caefee3SMatthias Ringwald  *    personal benefit and not for any commercial purpose or for
188caefee3SMatthias Ringwald  *    monetary gain.
198caefee3SMatthias Ringwald  *
208caefee3SMatthias Ringwald  * THIS SOFTWARE IS PROVIDED BY BLUEKITCHEN GMBH AND CONTRIBUTORS
218caefee3SMatthias Ringwald  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
228caefee3SMatthias 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,
258caefee3SMatthias Ringwald  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
268caefee3SMatthias Ringwald  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
278caefee3SMatthias Ringwald  * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
288caefee3SMatthias Ringwald  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
298caefee3SMatthias Ringwald  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
308caefee3SMatthias Ringwald  * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
318caefee3SMatthias Ringwald  * SUCH DAMAGE.
328caefee3SMatthias Ringwald  *
338caefee3SMatthias Ringwald  * Please inquire about commercial licensing options at
348caefee3SMatthias Ringwald  * [email protected]
358caefee3SMatthias Ringwald  *
368caefee3SMatthias Ringwald  */
378caefee3SMatthias Ringwald 
38f11fd9a9SMatthias Ringwald #define BTSTACK_FILE__ "main.c"
39ab2c6ae4SMatthias Ringwald 
408caefee3SMatthias Ringwald // *****************************************************************************
418caefee3SMatthias Ringwald //
428caefee3SMatthias Ringwald // minimal setup for HCI code
438caefee3SMatthias Ringwald //
448caefee3SMatthias Ringwald // *****************************************************************************
458caefee3SMatthias Ringwald 
468caefee3SMatthias Ringwald #include <stdint.h>
478caefee3SMatthias Ringwald #include <stdio.h>
488caefee3SMatthias Ringwald #include <stdlib.h>
498caefee3SMatthias Ringwald #include <string.h>
508caefee3SMatthias Ringwald #include <signal.h>
5181cd68f5SMatthias Ringwald #include <unistd.h>
5281cd68f5SMatthias Ringwald #include <getopt.h>
538caefee3SMatthias Ringwald 
547907f069SMatthias Ringwald #include "btstack_config.h"
558caefee3SMatthias Ringwald 
56f11fd9a9SMatthias Ringwald #include "ble/le_device_db_tlv.h"
57f11fd9a9SMatthias Ringwald #include "bluetooth_company_id.h"
5871e722a7SMatthias Ringwald #include "btstack_audio.h"
59f11fd9a9SMatthias Ringwald #include "btstack_chipset_bcm.h"
60f11fd9a9SMatthias Ringwald #include "btstack_chipset_cc256x.h"
61f11fd9a9SMatthias Ringwald #include "btstack_chipset_csr.h"
62f11fd9a9SMatthias Ringwald #include "btstack_chipset_em9301.h"
63f11fd9a9SMatthias Ringwald #include "btstack_chipset_stlc2500d.h"
64f11fd9a9SMatthias Ringwald #include "btstack_chipset_tc3566x.h"
651c61f116SMatthias Ringwald #include "btstack_chipset_zephyr.h"
6616ece135SMatthias Ringwald #include "btstack_debug.h"
67e392c21bSMatthias Ringwald #include "btstack_event.h"
6854b584ffSMatthias Ringwald #include "btstack_memory.h"
6982636622SMatthias Ringwald #include "btstack_run_loop.h"
708f2a52f4SMatthias Ringwald #include "btstack_run_loop_posix.h"
71f11fd9a9SMatthias Ringwald #include "btstack_signal.h"
72f11fd9a9SMatthias Ringwald #include "btstack_stdin.h"
73f11fd9a9SMatthias Ringwald #include "btstack_tlv_posix.h"
74793a0509SMatthias Ringwald #include "btstack_uart.h"
75f11fd9a9SMatthias Ringwald #include "classic/btstack_link_key_db_tlv.h"
7654b584ffSMatthias Ringwald #include "hci.h"
7754b584ffSMatthias Ringwald #include "hci_dump.h"
787435ec7bSMatthias Ringwald #include "hci_dump_posix_fs.h"
79c8dfe071SMatthias Ringwald #include "hci_transport.h"
80c8dfe071SMatthias Ringwald #include "hci_transport_h4.h"
81c0cdcfe7SMatthias Ringwald 
8264eccac7SMatthias Ringwald 
837daa8bd9SMatthias Ringwald #define TLV_DB_PATH_PREFIX "/tmp/btstack_"
847daa8bd9SMatthias Ringwald #define TLV_DB_PATH_POSTFIX ".tlv"
857daa8bd9SMatthias Ringwald static char tlv_db_path[100];
8681cd68f5SMatthias Ringwald static bool tlv_reset;
877daa8bd9SMatthias Ringwald static const btstack_tlv_t * tlv_impl;
887daa8bd9SMatthias Ringwald static btstack_tlv_posix_t   tlv_context;
891c61f116SMatthias Ringwald static bd_addr_t             static_address;
901c61f116SMatthias Ringwald 
911c61f116SMatthias Ringwald // random MAC address for the device, used if nothing else is available
92e28aaf35SMatthias Ringwald static bd_addr_t random_address = { 0xC1, 0x01, 0x01, 0x01, 0x01, 0x01 };
937daa8bd9SMatthias Ringwald 
94793a0509SMatthias Ringwald static int is_bcm;
95f11fd9a9SMatthias Ringwald // shutdown
96f11fd9a9SMatthias Ringwald static bool shutdown_triggered;
97793a0509SMatthias Ringwald 
988caefee3SMatthias Ringwald int btstack_main(int argc, const char * argv[]);
99755bc585SMatthias Ringwald static void local_version_information_handler(uint8_t * packet);
1008caefee3SMatthias Ringwald 
1019796ebeaSMatthias Ringwald static hci_transport_config_uart_t config = {
102*5b67487bSMatthias Ringwald     .type = HCI_TRANSPORT_CONFIG_UART,
103*5b67487bSMatthias Ringwald     .baudrate_init = 115200,
104*5b67487bSMatthias Ringwald     .baudrate_main = 0,
105*5b67487bSMatthias Ringwald     .flowcontrol = 1,
1068caefee3SMatthias Ringwald };
1078caefee3SMatthias Ringwald 
108d356a6daSMatthias Ringwald static btstack_packet_callback_registration_t hci_event_callback_registration;
109d356a6daSMatthias Ringwald 
packet_handler(uint8_t packet_type,uint16_t channel,uint8_t * packet,uint16_t size)110d356a6daSMatthias Ringwald static void packet_handler (uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size){
111*5b67487bSMatthias Ringwald     UNUSED(channel);
1121c61f116SMatthias Ringwald     static bd_addr_t local_addr;
1131c61f116SMatthias Ringwald     const uint8_t *params;
114d356a6daSMatthias Ringwald     if (packet_type != HCI_EVENT_PACKET) return;
11564eccac7SMatthias Ringwald     switch (hci_event_packet_get_type(packet)){
11664eccac7SMatthias Ringwald         case BTSTACK_EVENT_STATE:
117f11fd9a9SMatthias Ringwald             switch(btstack_event_state_get_state(packet)){
118f11fd9a9SMatthias Ringwald                 case HCI_STATE_WORKING:
119f11fd9a9SMatthias Ringwald                     gap_local_bd_addr(local_addr);
1201c61f116SMatthias Ringwald                     if( btstack_is_null_bd_addr(local_addr) && !btstack_is_null_bd_addr(static_address) ) {
1211c61f116SMatthias Ringwald                         memcpy(local_addr, static_address, sizeof(bd_addr_t));
1221c61f116SMatthias Ringwald                     } else if( btstack_is_null_bd_addr(local_addr) && btstack_is_null_bd_addr(static_address) ) {
1231c61f116SMatthias Ringwald                         memcpy(local_addr, random_address, sizeof(bd_addr_t));
1241c61f116SMatthias Ringwald                         gap_random_address_set(local_addr);
1251c61f116SMatthias Ringwald                     }
1261c61f116SMatthias Ringwald 
127f11fd9a9SMatthias Ringwald                     printf("BTstack up and running on %s.\n", bd_addr_to_str(local_addr));
12854736c11SMatthias Ringwald                     btstack_strcpy(tlv_db_path, sizeof(tlv_db_path), TLV_DB_PATH_PREFIX);
12954736c11SMatthias Ringwald                     btstack_strcat(tlv_db_path, sizeof(tlv_db_path), bd_addr_to_str_with_delimiter(local_addr, '-'));
13054736c11SMatthias Ringwald                     btstack_strcat(tlv_db_path, sizeof(tlv_db_path), TLV_DB_PATH_POSTFIX);
13181cd68f5SMatthias Ringwald                     printf("TLV path: %s", tlv_db_path);
13281cd68f5SMatthias Ringwald                     if (tlv_reset){
13381cd68f5SMatthias Ringwald                         int rc = unlink(tlv_db_path);
13481cd68f5SMatthias Ringwald                         if (rc == 0) {
13581cd68f5SMatthias Ringwald                             printf(", reset ok");
13681cd68f5SMatthias Ringwald                         } else {
13781cd68f5SMatthias Ringwald                             printf(", reset failed with result = %d", rc);
13881cd68f5SMatthias Ringwald                         }
13981cd68f5SMatthias Ringwald                     }
14081cd68f5SMatthias Ringwald                     printf("\n");
1417daa8bd9SMatthias Ringwald                     tlv_impl = btstack_tlv_posix_init_instance(&tlv_context, tlv_db_path);
1427daa8bd9SMatthias Ringwald                     btstack_tlv_set_instance(tlv_impl, &tlv_context);
14381862996SMatthias Ringwald #ifdef ENABLE_CLASSIC
14481862996SMatthias Ringwald                     hci_set_link_key_db(btstack_link_key_db_tlv_get_instance(tlv_impl, &tlv_context));
14581862996SMatthias Ringwald #endif
14681862996SMatthias Ringwald #ifdef ENABLE_BLE
14781862996SMatthias Ringwald                     le_device_db_tlv_configure(tlv_impl, &tlv_context);
14881862996SMatthias Ringwald #endif
14964eccac7SMatthias Ringwald                     break;
150f11fd9a9SMatthias Ringwald                 case HCI_STATE_OFF:
151f11fd9a9SMatthias Ringwald                     btstack_tlv_posix_deinit(&tlv_context);
152f11fd9a9SMatthias Ringwald                     if (!shutdown_triggered) break;
153f11fd9a9SMatthias Ringwald                     // reset stdin
154f11fd9a9SMatthias Ringwald                     btstack_stdin_reset();
155f11fd9a9SMatthias Ringwald                     log_info("Good bye, see you.\n");
156f11fd9a9SMatthias Ringwald                     exit(0);
157f11fd9a9SMatthias Ringwald                     break;
158f11fd9a9SMatthias Ringwald                 default:
159f11fd9a9SMatthias Ringwald                     break;
160f11fd9a9SMatthias Ringwald             }
161f11fd9a9SMatthias Ringwald             break;
16264eccac7SMatthias Ringwald         case HCI_EVENT_COMMAND_COMPLETE:
1631c61f116SMatthias Ringwald             switch (hci_event_command_complete_get_command_opcode(packet)){
1641c61f116SMatthias Ringwald                 case HCI_OPCODE_HCI_READ_LOCAL_VERSION_INFORMATION:
1651c61f116SMatthias Ringwald                     local_version_information_handler(packet);
1661c61f116SMatthias Ringwald                     break;
1671c61f116SMatthias Ringwald                 case HCI_OPCODE_HCI_ZEPHYR_READ_STATIC_ADDRESS:
1681c61f116SMatthias Ringwald                     log_info("Zephyr read static address available");
1691c61f116SMatthias Ringwald                     params = hci_event_command_complete_get_return_parameters(packet);
1701c61f116SMatthias Ringwald                     if(params[0] != 0)
1711c61f116SMatthias Ringwald                         break;
1721c61f116SMatthias Ringwald                     if(size < 13)
1731c61f116SMatthias Ringwald                         break;
1741c61f116SMatthias Ringwald                     reverse_48(&params[2], static_address);
1751c61f116SMatthias Ringwald                     gap_random_address_set(static_address);
1761c61f116SMatthias Ringwald                     break;
1771c61f116SMatthias Ringwald                 case HCI_OPCODE_HCI_READ_LOCAL_NAME:
1781c61f116SMatthias Ringwald                     params = hci_event_command_complete_get_return_parameters(packet);
1791c61f116SMatthias Ringwald                     if(params[0] != 0)
1801c61f116SMatthias Ringwald                         break;
18164eccac7SMatthias Ringwald                     // terminate, name 248 chars
18264eccac7SMatthias Ringwald                     packet[6+248] = 0;
18364eccac7SMatthias Ringwald                     printf("Local name: %s\n", &packet[6]);
18464eccac7SMatthias Ringwald                     if (is_bcm){
18564eccac7SMatthias Ringwald                         btstack_chipset_bcm_set_device_name((const char *)&packet[6]);
18664eccac7SMatthias Ringwald                     }
1871c61f116SMatthias Ringwald                     break;
1881c61f116SMatthias Ringwald                 default:
1891c61f116SMatthias Ringwald                     break;
190755bc585SMatthias Ringwald             }
19164eccac7SMatthias Ringwald             break;
1921c61f116SMatthias Ringwald 
19364eccac7SMatthias Ringwald         default:
19464eccac7SMatthias Ringwald             break;
19564eccac7SMatthias Ringwald     }
196d356a6daSMatthias Ringwald }
197d356a6daSMatthias Ringwald 
trigger_shutdown(void)198f11fd9a9SMatthias Ringwald static void trigger_shutdown(void){
199b96c8f44SMatthias Ringwald     printf("CTRL-C - SIGINT received, shutting down..\n");
200b96c8f44SMatthias Ringwald     log_info("sigint_handler: shutting down");
201f11fd9a9SMatthias Ringwald     shutdown_triggered = true;
2028caefee3SMatthias Ringwald     hci_power_control(HCI_POWER_OFF);
203113487d2SDirk Helbig     btstack_stdin_reset();
2048caefee3SMatthias Ringwald }
2058caefee3SMatthias Ringwald 
2068caefee3SMatthias Ringwald static int led_state = 0;
hal_led_toggle(void)2078caefee3SMatthias Ringwald void hal_led_toggle(void){
2088caefee3SMatthias Ringwald     led_state = 1 - led_state;
2098caefee3SMatthias Ringwald     printf("LED State %u\n", led_state);
2108caefee3SMatthias Ringwald }
use_fast_uart(void)2113250103aSMatthias Ringwald static void use_fast_uart(void){
2122c2bf480SMatthias Ringwald     printf("Using 921600 baud.\n");
2132c2bf480SMatthias Ringwald     config.baudrate_main = 921600;
2142c2bf480SMatthias Ringwald }
2158caefee3SMatthias Ringwald 
local_version_information_handler(uint8_t * packet)216755bc585SMatthias Ringwald static void local_version_information_handler(uint8_t * packet){
217c0cdcfe7SMatthias Ringwald     printf("Local version information:\n");
2185c2e0bddSMatthias Ringwald     uint16_t hci_version    = packet[6];
2195c2e0bddSMatthias Ringwald     uint16_t hci_revision   = little_endian_read_16(packet, 7);
2205c2e0bddSMatthias Ringwald     uint16_t lmp_version    = packet[9];
221f8fbdce0SMatthias Ringwald     uint16_t manufacturer   = little_endian_read_16(packet, 10);
222f8fbdce0SMatthias Ringwald     uint16_t lmp_subversion = little_endian_read_16(packet, 12);
223c0cdcfe7SMatthias Ringwald     printf("- HCI Version    0x%04x\n", hci_version);
224c0cdcfe7SMatthias Ringwald     printf("- HCI Revision   0x%04x\n", hci_revision);
225c0cdcfe7SMatthias Ringwald     printf("- LMP Version    0x%04x\n", lmp_version);
226755bc585SMatthias Ringwald     printf("- LMP Subversion 0x%04x\n", lmp_subversion);
227c0cdcfe7SMatthias Ringwald     printf("- Manufacturer 0x%04x\n", manufacturer);
228c0cdcfe7SMatthias Ringwald     switch (manufacturer){
22961f37892SMatthias Ringwald         case BLUETOOTH_COMPANY_ID_CAMBRIDGE_SILICON_RADIO:
23099dd7845SMatthias Ringwald             printf("Cambridge Silicon Radio - CSR chipset, Build ID: %u.\n", hci_revision);
2313250103aSMatthias Ringwald             use_fast_uart();
232c0cdcfe7SMatthias Ringwald             hci_set_chipset(btstack_chipset_csr_instance());
233c0cdcfe7SMatthias Ringwald             break;
23461f37892SMatthias Ringwald         case BLUETOOTH_COMPANY_ID_TEXAS_INSTRUMENTS_INC:
235c0cdcfe7SMatthias Ringwald             printf("Texas Instruments - CC256x compatible chipset.\n");
236ed5d91baSMatthias Ringwald             if (lmp_subversion != btstack_chipset_cc256x_lmp_subversion()){
237ed5d91baSMatthias Ringwald                 printf("Error: LMP Subversion does not match initscript! ");
238ed5d91baSMatthias Ringwald                 printf("Your initscripts is for %s chipset\n", btstack_chipset_cc256x_lmp_subversion() < lmp_subversion ? "an older" : "a newer");
239ed5d91baSMatthias Ringwald                 printf("Please update Makefile to include the appropriate bluetooth_init_cc256???.c file\n");
240ed5d91baSMatthias Ringwald                 exit(10);
241ed5d91baSMatthias Ringwald             }
2423250103aSMatthias Ringwald             use_fast_uart();
243c0cdcfe7SMatthias Ringwald             hci_set_chipset(btstack_chipset_cc256x_instance());
244f6a20ec9SMatthias Ringwald #ifdef ENABLE_EHCILL
245f6a20ec9SMatthias Ringwald             printf("eHCILL enabled.\n");
2468c768b83SMatthias Ringwald #else
2478c768b83SMatthias Ringwald             printf("eHCILL disable.\n");
2488a23fc53SMatthias Ringwald #endif
249ed5d91baSMatthias Ringwald 
250c0cdcfe7SMatthias Ringwald             break;
25161f37892SMatthias Ringwald         case BLUETOOTH_COMPANY_ID_BROADCOM_CORPORATION:
252c21d89f3SMatthias Ringwald             printf("Broadcom/Cypress - using BCM driver.\n");
2531ccd94aaSMatthias Ringwald             hci_set_chipset(btstack_chipset_bcm_instance());
254fc1ce773SMatthias Ringwald             use_fast_uart();
25564eccac7SMatthias Ringwald             is_bcm = 1;
256c0cdcfe7SMatthias Ringwald             break;
25761f37892SMatthias Ringwald         case BLUETOOTH_COMPANY_ID_ST_MICROELECTRONICS:
258c0cdcfe7SMatthias Ringwald             printf("ST Microelectronics - using STLC2500d driver.\n");
2593250103aSMatthias Ringwald             use_fast_uart();
260c0cdcfe7SMatthias Ringwald             hci_set_chipset(btstack_chipset_stlc2500d_instance());
261c0cdcfe7SMatthias Ringwald             break;
2623e05a31cSMatthias Ringwald         case BLUETOOTH_COMPANY_ID_EM_MICROELECTRONIC_MARIN_SA:
263c0cdcfe7SMatthias Ringwald             printf("EM Microelectronics - using EM9301 driver.\n");
264c0cdcfe7SMatthias Ringwald             hci_set_chipset(btstack_chipset_em9301_instance());
26507b68b69SMatthias Ringwald             use_fast_uart();
266c0cdcfe7SMatthias Ringwald             break;
26761f37892SMatthias Ringwald         case BLUETOOTH_COMPANY_ID_NORDIC_SEMICONDUCTOR_ASA:
26864eccac7SMatthias Ringwald             printf("Nordic Semiconductor nRF5 chipset.\n");
269ff479fcfSMatthias Ringwald             hci_set_chipset(btstack_chipset_zephyr_instance());
270ff479fcfSMatthias Ringwald             break;
271ff479fcfSMatthias Ringwald         case BLUETOOTH_COMPANY_ID_THE_LINUX_FOUNDATION:
272ff479fcfSMatthias Ringwald             printf("Linux Foundation - assuming Zephyr running on Nordic chipset.\n");
273ff479fcfSMatthias Ringwald             hci_set_chipset(btstack_chipset_zephyr_instance());
27457c1ace8SMatthias Ringwald             break;
275c5541f68SMatthias Ringwald         case BLUETOOTH_COMPANY_ID_TOSHIBA_CORP:
276c5541f68SMatthias Ringwald             printf("Toshiba - using TC3566x driver.\n");
277c5541f68SMatthias Ringwald             hci_set_chipset(btstack_chipset_tc3566x_instance());
278c5541f68SMatthias Ringwald             use_fast_uart();
279c5541f68SMatthias Ringwald             break;
2802f50bc44SMatthias Ringwald         case BLUETOOTH_COMPANY_ID_PACKETCRAFT_INC:
2812f50bc44SMatthias Ringwald             printf("PacketCraft HCI Controller\n");
2821c61f116SMatthias Ringwald             hci_set_chipset(btstack_chipset_zephyr_instance());
2832f50bc44SMatthias Ringwald             break;
284c0cdcfe7SMatthias Ringwald         default:
285c0cdcfe7SMatthias Ringwald             printf("Unknown manufacturer / manufacturer not supported yet.\n");
286c0cdcfe7SMatthias Ringwald             break;
287c0cdcfe7SMatthias Ringwald     }
288c0cdcfe7SMatthias Ringwald }
289c0cdcfe7SMatthias Ringwald 
2901ab12960SMatthias Ringwald static char short_options[] = "+hu:l:rb:";
29181cd68f5SMatthias Ringwald 
29281cd68f5SMatthias Ringwald static struct option long_options[] = {
29381cd68f5SMatthias Ringwald         {"help",        no_argument,        NULL,   'h'},
29481cd68f5SMatthias Ringwald         {"logfile",    required_argument,  NULL,   'l'},
29581cd68f5SMatthias Ringwald         {"reset-tlv",    no_argument,       NULL,   'r'},
29681cd68f5SMatthias Ringwald         {"tty",    required_argument,  NULL,   'u'},
297e28aaf35SMatthias Ringwald         {"bd-addr", required_argument, NULL, 'b'},
29881cd68f5SMatthias Ringwald         {0, 0, 0, 0}
29981cd68f5SMatthias Ringwald };
30081cd68f5SMatthias Ringwald 
30181cd68f5SMatthias Ringwald static char *help_options[] = {
30281cd68f5SMatthias Ringwald         "print (this) help.",
30381cd68f5SMatthias Ringwald         "set file to store debug output and HCI trace.",
30481cd68f5SMatthias Ringwald         "reset bonding information stored in TLV.",
30581cd68f5SMatthias Ringwald         "set path to Bluetooth Controller.",
306e28aaf35SMatthias Ringwald         "set random static Bluetooth address for nRF5340 with PacketCraft Controller.",
30781cd68f5SMatthias Ringwald };
30881cd68f5SMatthias Ringwald 
30981cd68f5SMatthias Ringwald static char *option_arg_name[] = {
31081cd68f5SMatthias Ringwald         "",
31181cd68f5SMatthias Ringwald         "LOGFILE",
31281cd68f5SMatthias Ringwald         "",
31381cd68f5SMatthias Ringwald         "TTY",
314e28aaf35SMatthias Ringwald         "BD_ADDR",
31581cd68f5SMatthias Ringwald };
31681cd68f5SMatthias Ringwald 
usage(const char * name)31781cd68f5SMatthias Ringwald static void usage(const char *name){
31881cd68f5SMatthias Ringwald     unsigned int i;
31981cd68f5SMatthias Ringwald     printf( "usage:\n\t%s [options]\n", name );
32081cd68f5SMatthias Ringwald     printf("valid options:\n");
32181cd68f5SMatthias Ringwald     for( i=0; long_options[i].name != 0; i++) {
32281cd68f5SMatthias Ringwald         printf("--%-10s| -%c  %-10s\t\t%s\n", long_options[i].name, long_options[i].val, option_arg_name[i], help_options[i] );
32381cd68f5SMatthias Ringwald     }
32481cd68f5SMatthias Ringwald }
32581cd68f5SMatthias Ringwald 
main(int argc,const char * argv[])3268caefee3SMatthias Ringwald int main(int argc, const char * argv[]){
3278caefee3SMatthias Ringwald 
32881cd68f5SMatthias Ringwald     const char * log_file_path = NULL;
32981cd68f5SMatthias Ringwald 
33081cd68f5SMatthias Ringwald     // set default device path
33181cd68f5SMatthias Ringwald     config.device_name = "/dev/tty.usbmodemEF437DF524C51";
3321ab12960SMatthias Ringwald     int oldopterr = opterr;
3331ab12960SMatthias Ringwald     opterr = 0;
33481cd68f5SMatthias Ringwald     // parse command line parameters
33581cd68f5SMatthias Ringwald     while(true){
33681cd68f5SMatthias Ringwald         int c = getopt_long( argc, (char* const *)argv, short_options, long_options, NULL );
33781cd68f5SMatthias Ringwald         if (c < 0) {
33881cd68f5SMatthias Ringwald             break;
33981cd68f5SMatthias Ringwald         }
34081cd68f5SMatthias Ringwald         if (c == '?'){
3411ab12960SMatthias Ringwald             continue;
34281cd68f5SMatthias Ringwald         }
34381cd68f5SMatthias Ringwald         switch (c) {
34481cd68f5SMatthias Ringwald             case 'u':
34581cd68f5SMatthias Ringwald                 config.device_name = optarg;
34681cd68f5SMatthias Ringwald                 break;
34781cd68f5SMatthias Ringwald             case 'l':
34881cd68f5SMatthias Ringwald                 log_file_path = optarg;
34981cd68f5SMatthias Ringwald                 break;
35081cd68f5SMatthias Ringwald             case 'r':
35181cd68f5SMatthias Ringwald                 tlv_reset = true;
35281cd68f5SMatthias Ringwald                 break;
353e28aaf35SMatthias Ringwald             case 'b':
354e28aaf35SMatthias Ringwald                 sscanf_bd_addr(optarg, random_address);
355e28aaf35SMatthias Ringwald                 break;
35681cd68f5SMatthias Ringwald             case 'h':
35781cd68f5SMatthias Ringwald             default:
35881cd68f5SMatthias Ringwald                 usage(argv[0]);
3591ab12960SMatthias Ringwald                 break;
36081cd68f5SMatthias Ringwald         }
36181cd68f5SMatthias Ringwald     }
3621ab12960SMatthias Ringwald     // reset getopt parsing, so it works as intended from btstack_main
3631ab12960SMatthias Ringwald     optind = 1;
3641ab12960SMatthias Ringwald     opterr = oldopterr;
3651ab12960SMatthias Ringwald 
3668caefee3SMatthias Ringwald     /// GET STARTED with BTstack ///
3678caefee3SMatthias Ringwald 	btstack_memory_init();
368528a4a3bSMatthias Ringwald     btstack_run_loop_init(btstack_run_loop_posix_get_instance());
3698caefee3SMatthias Ringwald 
3707435ec7bSMatthias Ringwald     // log into file using HCI_DUMP_PACKETLOGGER format
37181cd68f5SMatthias Ringwald     if (log_file_path == NULL){
37281cd68f5SMatthias Ringwald         log_file_path = "/tmp/hci_dump.pklg";
37381cd68f5SMatthias Ringwald     }
37481cd68f5SMatthias Ringwald     hci_dump_posix_fs_open(log_file_path, HCI_DUMP_PACKETLOGGER);
3757435ec7bSMatthias Ringwald     const hci_dump_t * hci_dump_impl = hci_dump_posix_fs_get_instance();
3767435ec7bSMatthias Ringwald     hci_dump_init(hci_dump_impl);
37781cd68f5SMatthias Ringwald     printf("Packet Log: %s\n", log_file_path);
3788caefee3SMatthias Ringwald 
379c5ee5b32SMatthias Ringwald     printf("H4 device: %s\n", config.device_name);
380c5ee5b32SMatthias Ringwald 
3818caefee3SMatthias Ringwald     // init HCI
382793a0509SMatthias Ringwald     const btstack_uart_t * uart_driver = btstack_uart_posix_instance();
383793a0509SMatthias Ringwald 	const hci_transport_t * transport = hci_transport_h4_instance_for_uart(uart_driver);
3842d5e09d6SMatthias Ringwald 	hci_init(transport, (void*) &config);
38577b95b41SMatthias Ringwald 
38671e722a7SMatthias Ringwald #ifdef HAVE_PORTAUDIO
38771e722a7SMatthias Ringwald     btstack_audio_sink_set_instance(btstack_audio_portaudio_sink_get_instance());
38871e722a7SMatthias Ringwald     btstack_audio_source_set_instance(btstack_audio_portaudio_source_get_instance());
38971e722a7SMatthias Ringwald #endif
39071e722a7SMatthias Ringwald 
39177b95b41SMatthias Ringwald     // set BD_ADDR for CSR without Flash/unique address
39277b95b41SMatthias Ringwald     // bd_addr_t own_address = { 0x11, 0x22, 0x33, 0x44, 0x55, 0x66};
39377b95b41SMatthias Ringwald     // btstack_chipset_csr_set_bd_addr(own_address);
3948caefee3SMatthias Ringwald 
395d356a6daSMatthias Ringwald     // inform about BTstack state
396d356a6daSMatthias Ringwald     hci_event_callback_registration.callback = &packet_handler;
397d356a6daSMatthias Ringwald     hci_add_event_handler(&hci_event_callback_registration);
398d356a6daSMatthias Ringwald 
399f11fd9a9SMatthias Ringwald     // register callback for CTRL-c
400f11fd9a9SMatthias Ringwald     btstack_signal_register_callback(SIGINT, &trigger_shutdown);
4018caefee3SMatthias Ringwald 
4028caefee3SMatthias Ringwald     // setup app
4038caefee3SMatthias Ringwald     btstack_main(argc, argv);
4048caefee3SMatthias Ringwald 
4058caefee3SMatthias Ringwald     // go
406528a4a3bSMatthias Ringwald     btstack_run_loop_execute();
4078caefee3SMatthias Ringwald 
408113487d2SDirk Helbig     btstack_stdin_reset();
4098caefee3SMatthias Ringwald     return 0;
4108caefee3SMatthias Ringwald }
411