@@ -33,9 +33,9 @@ static volatile BTState bluetoothState = BT_OFF;
3333
3434#include < BleBatteryService.h>
3535
36- BTSerialInterface *bluetoothSerialSpp;
37- BTSerialInterface *bluetoothSerialBle;
38- BTSerialInterface *bluetoothSerialBleCommands; // Second BLE serial for CLI interface to mobile app
36+ BTSerialInterface *bluetoothSerialSpp = nullptr ;
37+ BTSerialInterface *bluetoothSerialBle = nullptr ;
38+ BTSerialInterface *bluetoothSerialBleCommands = nullptr ; // Second BLE serial for CLI interface to mobile app
3939BleBatteryService bluetoothBatteryService;
4040
4141#define BLE_SERVICE_UUID " 6e400001-b5a3-f393-e0a9-e50e24dcca9e"
@@ -48,6 +48,8 @@ BleBatteryService bluetoothBatteryService;
4848
4949TaskHandle_t bluetoothCommandTaskHandle = nullptr ; // Task to monitor incoming CLI from BLE
5050
51+ BluetoothRadioType_e bluetoothRadioPreviousOnType = BLUETOOTH_RADIO_OFF;
52+
5153#endif // COMPILE_BT
5254
5355// ----------------------------------------
@@ -174,6 +176,9 @@ byte bluetoothGetState()
174176int bluetoothRead (uint8_t *buffer, int length)
175177{
176178#ifdef COMPILE_BT
179+ if (bluetoothGetState () == BT_OFF)
180+ return 0 ;
181+
177182 if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE)
178183 {
179184 int bytesRead = 0 ;
@@ -223,6 +228,9 @@ int bluetoothCommandRead(uint8_t *buffer, int length)
223228uint8_t bluetoothRead ()
224229{
225230#ifdef COMPILE_BT
231+ if (bluetoothGetState () == BT_OFF)
232+ return 0 ;
233+
226234 if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE)
227235 {
228236 // Give incoming BLE the priority
@@ -261,6 +269,9 @@ uint8_t bluetoothCommandRead()
261269int bluetoothRxDataAvailable ()
262270{
263271#ifdef COMPILE_BT
272+ if (bluetoothGetState () == BT_OFF)
273+ return 0 ;
274+
264275 if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE)
265276 {
266277 // Give incoming BLE the priority
@@ -299,6 +310,9 @@ int bluetoothCommandAvailable()
299310int bluetoothWrite (const uint8_t *buffer, int length)
300311{
301312#ifdef COMPILE_BT
313+ if (bluetoothGetState () == BT_OFF)
314+ return length; // Avoid buffer full warnings
315+
302316 if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE)
303317 {
304318 // Write to both interfaces
@@ -365,6 +379,9 @@ int bluetoothCommandWrite(const uint8_t *buffer, int length)
365379int bluetoothWrite (uint8_t value)
366380{
367381#ifdef COMPILE_BT
382+ if (bluetoothGetState () == BT_OFF)
383+ return 1 ; // Avoid buffer full warnings
384+
368385 if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE)
369386 {
370387 // Write to both interfaces
@@ -399,6 +416,9 @@ int bluetoothWrite(uint8_t value)
399416void bluetoothFlush ()
400417{
401418#ifdef COMPILE_BT
419+ if (bluetoothGetState () == BT_OFF)
420+ return ;
421+
402422 if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE)
403423 {
404424 bluetoothSerialBle->flush ();
@@ -420,76 +440,116 @@ void bluetoothFlush()
420440}
421441
422442void BTConfirmRequestCallback (uint32_t numVal) {
443+ if (bluetoothGetState () == BT_OFF)
444+ return ;
445+
423446 systemPrintf (" Device sent PIN: %06lu. Sending confirmation\r\n " , numVal);
424447 bluetoothSerialSpp->confirmReply (true ); // AUTO_PAIR - equivalent to enableSSP(false, true);
425448 // TODO: if the RTK device has an OLED, we should display the PIN so user can confirm
426449}
427450
428- // Get MAC, start radio
429- // Tack device's MAC address to end of friendly broadcast name
430- // This allows multiple units to be on at same time
451+ void deviceNameSpacesToUnderscores ()
452+ {
453+ for (size_t i = 0 ; i < strlen (deviceName); i++)
454+ {
455+ if (deviceName[i] == ' ' )
456+ deviceName[i] = ' _' ;
457+ }
458+ }
459+
460+ void deviceNameUnderscoresToSpaces ()
461+ {
462+ for (size_t i = 0 ; i < strlen (deviceName); i++)
463+ {
464+ if (deviceName[i] == ' _' )
465+ deviceName[i] = ' ' ;
466+ }
467+ }
468+
469+ // Begin Bluetooth with a broadcast name of 'SparkFun Postcard-XXXX' or 'SparkPNT Facet mosaicX5-XXXX'
470+ // Add 4 characters of device's MAC address to end of the broadcast name
471+ // This allows users to discern between multiple devices in the local area
431472void bluetoothStart ()
473+ {
474+ bluetoothStart (false );
475+ }
476+ void bluetoothStartSkipOnlineCheck ()
477+ {
478+ bluetoothStart (true );
479+ }
480+ void bluetoothStart (bool skipOnlineCheck)
432481{
433482 if (settings.bluetoothRadioType == BLUETOOTH_RADIO_OFF)
434483 return ;
435484
436- #ifdef COMPILE_BT
437- if (!online.bluetooth )
485+ if (!skipOnlineCheck)
438486 {
439- bluetoothState = BT_OFF;
440- char stateName[11 ] = {0 };
441- if (inRoverMode () == true )
442- strncpy (stateName, " Rover-" , sizeof (stateName) - 1 );
443- else if (inBaseMode () == true )
444- strncpy (stateName, " Base-" , sizeof (stateName) - 1 );
445- else
487+ if (online.bluetooth )
446488 {
447- strncpy (stateName, " Rover-" , sizeof (stateName) - 1 );
448- log_d (" State out of range for Bluetooth Broadcast: %d" , systemState);
489+ return ;
449490 }
491+ }
492+
493+ #ifdef COMPILE_BT
494+ { // Maintain the indentation for now. TODO: delete the braces and correct indentation
495+ bluetoothState = BT_OFF; // Indicate to tasks that BT is unavailable
450496
451497 char productName[50 ] = {0 };
452498 strncpy (productName, platformPrefix, sizeof (productName));
453499
454- // BLE is limited to ~28 characters in the device name. Shorten platformPrefix if needed.
455- if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE ||
456- settings.bluetoothRadioType == BLUETOOTH_RADIO_BLE)
457- {
458- if (strcmp (productName, " Facet L-Band Direct" ) == 0 )
459- {
460- strncpy (productName, " Facet L-Band" , sizeof (productName));
461- }
462- }
463-
464- snprintf (deviceName, sizeof (deviceName), " %s %s%02X%02X" , productName, stateName, btMACAddress[4 ],
500+ // Longest platform prefix is currently "Facet mosaicX5". We are just OK.
501+ // We currently don't need this:
502+ // // BLE is limited to ~28 characters in the device name. Shorten platformPrefix if needed.
503+ // if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE ||
504+ // settings.bluetoothRadioType == BLUETOOTH_RADIO_BLE)
505+ // {
506+ // if (strcmp(productName, "LONG PLATFORM PREFIX") == 0)
507+ // {
508+ // strncpy(productName, "SHORTER PREFIX", sizeof(productName));
509+ // }
510+ // }
511+
512+ RTKBrandAttribute *brandAttributes = getBrandAttributeFromBrand (present.brand );
513+
514+ snprintf (deviceName, sizeof (deviceName), " %s %s-%02X%02X" , brandAttributes->name , productName, btMACAddress[4 ],
465515 btMACAddress[5 ]);
466516
467- if (strlen (deviceName) > 28 )
517+ if (strlen (deviceName) > 28 ) // "SparkPNT Facet mosaicX5-ABCD" = 28 chars. We are just OK
468518 {
469- if (ENABLE_DEVELOPER)
470- systemPrintf (
471- " Warning! The Bluetooth device name '%s' is %d characters long. It may not work in BLE mode.\r\n " ,
472- deviceName, strlen (deviceName));
519+ // BLE will fail quietly if broadcast name is more than 28 characters
520+ systemPrintf (
521+ " ERROR! The Bluetooth device name \" %s\" is %d characters long. It will not work in BLE mode.\r\n " ,
522+ deviceName, strlen (deviceName));
523+ reportFatalError (" Bluetooth device name is longer than 28 characters." );
473524 }
474525
475526 // Select Bluetooth setup
476- if (settings.bluetoothRadioType == BLUETOOTH_RADIO_OFF)
477- return ;
478- else if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE)
527+ if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE)
479528 {
480- bluetoothSerialSpp = new BTClassicSerial ();
481- bluetoothSerialBle = new BTLESerial ();
482- bluetoothSerialBleCommands = new BTLESerial ();
529+ if (bluetoothSerialSpp == nullptr )
530+ bluetoothSerialSpp = new BTClassicSerial ();
531+ if (bluetoothSerialBle == nullptr )
532+ bluetoothSerialBle = new BTLESerial ();
533+ if (bluetoothSerialBleCommands == nullptr )
534+ bluetoothSerialBleCommands = new BTLESerial ();
483535 }
484536 else if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP)
485- bluetoothSerialSpp = new BTClassicSerial ();
537+ {
538+ if (bluetoothSerialSpp == nullptr )
539+ bluetoothSerialSpp = new BTClassicSerial ();
540+ }
486541 else if (settings.bluetoothRadioType == BLUETOOTH_RADIO_BLE)
487542 {
488- bluetoothSerialBle = new BTLESerial ();
489- bluetoothSerialBleCommands = new BTLESerial ();
543+ if (bluetoothSerialBle == nullptr )
544+ bluetoothSerialBle = new BTLESerial ();
545+ if (bluetoothSerialBleCommands == nullptr )
546+ bluetoothSerialBleCommands = new BTLESerial ();
490547 }
491548 else if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_ACCESSORY_MODE)
492- bluetoothSerialSpp = new BTClassicSerial ();
549+ {
550+ if (bluetoothSerialSpp == nullptr )
551+ bluetoothSerialSpp = new BTClassicSerial ();
552+ }
493553
494554 // Not yet implemented
495555 // if (pinBluetoothTaskHandle == nullptr)
@@ -692,7 +752,8 @@ void bluetoothStart()
692752 bluetoothState = BT_NOTCONNECTED;
693753 reportHeapNow (false );
694754 online.bluetooth = true ;
695- }
755+ bluetoothRadioPreviousOnType = settings.bluetoothRadioType ;
756+ } // if (1)
696757#endif // COMPILE_BT
697758}
698759
@@ -721,46 +782,85 @@ void bluetoothStop()
721782#ifdef COMPILE_BT
722783 if (online.bluetooth )
723784 {
785+ if (settings.debugNetworkLayer )
786+ systemPrintln (" Bluetooth turning off" );
787+
788+ bluetoothState = BT_OFF; // Indicate to tasks that BT is unavailable
789+
790+ // Stop BLE Command Task if BLE is enabled
791+ if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE ||
792+ settings.bluetoothRadioType == BLUETOOTH_RADIO_BLE)
793+ {
794+ task.bluetoothCommandTaskStopRequest = true ;
795+ while (task.bluetoothCommandTaskRunning == true )
796+ delay (1 );
797+ }
798+
799+ // end and delete BT instances
724800 if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_AND_BLE)
725801 {
726802 bluetoothSerialBle->flush (); // Complete any transfers
727803 bluetoothSerialBle->disconnect (); // Drop any clients
728804 bluetoothSerialBle->end (); // Release resources
805+ // delete bluetoothSerialBle;
806+ // bluetoothSerialBle = nullptr;
729807
730808 bluetoothSerialBleCommands->flush (); // Complete any transfers
731809 bluetoothSerialBleCommands->disconnect (); // Drop any clients
732810 bluetoothSerialBleCommands->end (); // Release resources
811+ // delete bluetoothSerialBleCommands;
812+ // bluetoothSerialBleCommands = nullptr;
733813
734814 bluetoothSerialSpp->flush (); // Complete any transfers
735815 bluetoothSerialSpp->disconnect (); // Drop any clients
816+ bluetoothSerialSpp->register_callback (nullptr );
736817 bluetoothSerialSpp->end (); // Release resources
818+ bluetoothSerialSpp->memrelease (); // Release memory
819+ // delete bluetoothSerialSpp;
820+ // bluetoothSerialSpp = nullptr;
821+
822+ bluetoothBatteryService.end ();
737823 }
738824 else if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP)
739825 {
740826 bluetoothSerialSpp->flush (); // Complete any transfers
741827 bluetoothSerialSpp->disconnect (); // Drop any clients
828+ bluetoothSerialSpp->register_callback (nullptr );
742829 bluetoothSerialSpp->end (); // Release resources
830+ bluetoothSerialSpp->memrelease (); // Release memory
831+ // delete bluetoothSerialSpp;
832+ // bluetoothSerialSpp = nullptr;
743833 }
744834 else if (settings.bluetoothRadioType == BLUETOOTH_RADIO_BLE)
745835 {
746836 bluetoothSerialBle->flush (); // Complete any transfers
747837 bluetoothSerialBle->disconnect (); // Drop any clients
748838 bluetoothSerialBle->end (); // Release resources
839+ // delete bluetoothSerialBle;
840+ // bluetoothSerialBle = nullptr;
749841
750842 bluetoothSerialBleCommands->flush (); // Complete any transfers
751843 bluetoothSerialBleCommands->disconnect (); // Drop any clients
752844 bluetoothSerialBleCommands->end (); // Release resources
845+ // delete bluetoothSerialBleCommands;
846+ // bluetoothSerialBleCommands = nullptr;
847+
848+ bluetoothBatteryService.end ();
753849 }
754850 else if (settings.bluetoothRadioType == BLUETOOTH_RADIO_SPP_ACCESSORY_MODE)
755851 {
756852 bluetoothSerialSpp->flush (); // Complete any transfers
757853 bluetoothSerialSpp->disconnect (); // Drop any clients
854+ bluetoothSerialSpp->register_callback (nullptr );
758855 bluetoothSerialSpp->end (); // Release resources
856+ bluetoothSerialSpp->memrelease (); // Release memory
857+ // delete bluetoothSerialSpp;
858+ // bluetoothSerialSpp = nullptr;
759859 }
760860
761- log_d (" Bluetooth turned off" );
861+ if (settings.debugNetworkLayer )
862+ systemPrintln (" Bluetooth turned off" );
762863
763- bluetoothState = BT_OFF;
764864 reportHeapNow (false );
765865 online.bluetooth = false ;
766866 }
@@ -805,6 +905,13 @@ void bluetoothPrintStatus()
805905void bluetoothSendBatteryPercent (int batteryLevelPercent)
806906{
807907#ifdef COMPILE_BT
908+ if (bluetoothGetState () == BT_OFF)
909+ return ;
910+
911+ if ((settings.bluetoothRadioType != BLUETOOTH_RADIO_SPP_AND_BLE) &&
912+ (settings.bluetoothRadioType != BLUETOOTH_RADIO_BLE))
913+ return ;
914+
808915 bluetoothBatteryService.reportBatteryPercent (batteryLevelPercent);
809916#endif // COMPILE_BT
810917}
0 commit comments