Skip to content

Commit fb343cb

Browse files
committed
Fixed the bluedroid build issue in ESP32
- Fixed the build issue with bluedroid. - Added extended ble advertising support. - Implemented the missing bluedroid shutdown flow
1 parent ee49ebd commit fb343cb

File tree

1 file changed

+173
-18
lines changed

1 file changed

+173
-18
lines changed

src/platform/ESP32/bluedroid/BLEManagerImpl.cpp

+173-18
Original file line numberDiff line numberDiff line change
@@ -147,7 +147,6 @@ const uint16_t CHIPoBLEGATTAttrCount = sizeof(CHIPoBLEGATTAttrs) / sizeof(CHIPoB
147147
ChipDeviceScanner & mDeviceScanner = Internal::ChipDeviceScanner::GetInstance();
148148
#endif
149149
BLEManagerImpl BLEManagerImpl::sInstance;
150-
constexpr System::Clock::Timeout BLEManagerImpl::kFastAdvertiseTimeout;
151150
#ifdef CONFIG_ENABLE_ESP32_BLE_CONTROLLER
152151
static esp_gattc_char_elem_t * char_elem_result = NULL;
153152
static esp_gattc_descr_elem_t * descr_elem_result = NULL;
@@ -228,6 +227,23 @@ CHIP_ERROR BLEManagerImpl::_Init()
228227
return err;
229228
}
230229

230+
void BLEManagerImpl::_Shutdown()
231+
{
232+
CancelBleAdvTimeoutTimer();
233+
234+
BleLayer::Shutdown();
235+
mServiceMode = ConnectivityManager::kCHIPoBLEServiceMode_Disabled;
236+
237+
// selectively setting kGATTServiceStarted flag, in order to notify the state machine to stop the CHIPoBLE gatt service
238+
mFlags.ClearAll().Set(Flags::kGATTServiceStarted);
239+
240+
#ifdef CONFIG_ENABLE_ESP32_BLE_CONTROLLER
241+
OnChipBleConnectReceived = nullptr;
242+
#endif // CONFIG_ENABLE_ESP32_BLE_CONTROLLER
243+
244+
PlatformMgr().ScheduleWork(DriveBLEState, 0);
245+
}
246+
231247
CHIP_ERROR BLEManagerImpl::_SetAdvertisingEnabled(bool val)
232248
{
233249
CHIP_ERROR err = CHIP_NO_ERROR;
@@ -236,8 +252,7 @@ CHIP_ERROR BLEManagerImpl::_SetAdvertisingEnabled(bool val)
236252

237253
if (val)
238254
{
239-
mAdvertiseStartTime = System::SystemClock().GetMonotonicTimestamp();
240-
ReturnErrorOnFailure(DeviceLayer::SystemLayer().StartTimer(kFastAdvertiseTimeout, HandleFastAdvertisementTimer, this));
255+
StartBleAdvTimeoutTimer(CHIP_DEVICE_CONFIG_BLE_ADVERTISING_INTERVAL_CHANGE_TIME);
241256
}
242257
mFlags.Set(Flags::kFastAdvertisingEnabled, val);
243258
mFlags.Set(Flags::kAdvertisingRefreshNeeded, 1);
@@ -247,21 +262,29 @@ CHIP_ERROR BLEManagerImpl::_SetAdvertisingEnabled(bool val)
247262
return err;
248263
}
249264

250-
void BLEManagerImpl::HandleFastAdvertisementTimer(System::Layer * systemLayer, void * context)
251-
{
252-
static_cast<BLEManagerImpl *>(context)->HandleFastAdvertisementTimer();
253-
}
254-
255-
void BLEManagerImpl::HandleFastAdvertisementTimer()
265+
void BLEManagerImpl::BleAdvTimeoutHandler(System::Layer *, void *)
256266
{
257-
System::Clock::Timestamp currentTimestamp = System::SystemClock().GetMonotonicTimestamp();
258-
259-
if (currentTimestamp - mAdvertiseStartTime >= kFastAdvertiseTimeout)
267+
if (BLEMgrImpl().mFlags.Has(Flags::kFastAdvertisingEnabled))
268+
{
269+
ChipLogProgress(DeviceLayer, "bleAdv Timeout : Start slow advertisement");
270+
BLEMgrImpl().mFlags.Set(Flags::kFastAdvertisingEnabled, 0);
271+
BLEMgrImpl().mFlags.Set(Flags::kAdvertisingRefreshNeeded, 1);
272+
#if CHIP_DEVICE_CONFIG_BLE_EXT_ADVERTISING
273+
BLEMgrImpl().mFlags.Clear(Flags::kExtAdvertisingEnabled);
274+
BLEMgrImpl().StartBleAdvTimeoutTimer(CHIP_DEVICE_CONFIG_BLE_EXT_ADVERTISING_INTERVAL_CHANGE_TIME_MS);
275+
#endif
276+
}
277+
#if CHIP_DEVICE_CONFIG_BLE_EXT_ADVERTISING
278+
else
260279
{
261-
mFlags.Clear(Flags::kFastAdvertisingEnabled);
262-
mFlags.Set(Flags::kAdvertisingRefreshNeeded);
263-
PlatformMgr().ScheduleWork(DriveBLEState, 0);
280+
ChipLogProgress(DeviceLayer, "bleAdv Timeout : Start extended advertisement");
281+
BLEMgrImpl().mFlags.Set(Flags::kAdvertising);
282+
BLEMgrImpl().mFlags.Set(Flags::kExtAdvertisingEnabled);
283+
BLEMgr().SetAdvertisingMode(BLEAdvertisingMode::kSlowAdvertising);
284+
BLEMgrImpl().mFlags.Set(Flags::kAdvertisingRefreshNeeded, 1);
264285
}
286+
#endif
287+
PlatformMgr().ScheduleWork(DriveBLEState, 0);
265288
}
266289

267290
CHIP_ERROR BLEManagerImpl::_SetAdvertisingMode(BLEAdvertisingMode mode)
@@ -841,8 +864,8 @@ bool BLEManagerImpl::SendIndication(BLE_CONNECTION_OBJECT conId, const ChipBleUU
841864
#endif
842865

843866
// Set param need_confirm as false will send notification, otherwise indication.
844-
err = MapBLEError(
845-
esp_ble_gatts_send_indicate(mAppIf, conId, mTXCharAttrHandle, data->DataLength(), data->Start(), true /* need_confirm */));
867+
err = MapBLEError(esp_ble_gatts_send_indicate(mAppIf, conId, mTXCharAttrHandle, static_cast<uint16_t>(data->DataLength()),
868+
data->Start(), true /* need_confirm */));
846869
if (err != CHIP_NO_ERROR)
847870
{
848871
ChipLogError(DeviceLayer, "esp_ble_gatts_send_indicate() failed: %s", ErrorStr(err));
@@ -910,6 +933,25 @@ CHIP_ERROR BLEManagerImpl::MapBLEError(int bleErr)
910933
}
911934
}
912935

936+
void BLEManagerImpl::CancelBleAdvTimeoutTimer(void)
937+
{
938+
if (SystemLayer().IsTimerActive(BleAdvTimeoutHandler, nullptr))
939+
{
940+
SystemLayer().CancelTimer(BleAdvTimeoutHandler, nullptr);
941+
}
942+
}
943+
944+
void BLEManagerImpl::StartBleAdvTimeoutTimer(uint32_t aTimeoutInMs)
945+
{
946+
CancelBleAdvTimeoutTimer();
947+
948+
CHIP_ERROR err = SystemLayer().StartTimer(System::Clock::Milliseconds32(aTimeoutInMs), BleAdvTimeoutHandler, nullptr);
949+
if ((err != CHIP_NO_ERROR))
950+
{
951+
ChipLogError(DeviceLayer, "Failed to start BledAdv timeout timer");
952+
}
953+
}
954+
913955
void BLEManagerImpl::DriveBLEState(void)
914956
{
915957
CHIP_ERROR err = CHIP_NO_ERROR;
@@ -1033,7 +1075,8 @@ void BLEManagerImpl::DriveBLEState(void)
10331075
ExitNow();
10341076
}
10351077

1036-
mFlags.Set(Flags::kControlOpInProgress);
1078+
DeinitESPBleLayer();
1079+
mFlags.ClearAll();
10371080

10381081
ExitNow();
10391082
}
@@ -1136,6 +1179,25 @@ CHIP_ERROR BLEManagerImpl::InitESPBleLayer(void)
11361179
return err;
11371180
}
11381181

1182+
#ifndef CONFIG_IDF_TARGET_ESP32
1183+
esp_err_t bluedroid_set_random_address()
1184+
{
1185+
esp_bd_addr_t rand_addr;
1186+
1187+
esp_fill_random(rand_addr, sizeof(esp_bd_addr_t));
1188+
rand_addr[0] = (rand_addr[0] & 0x3F) | 0xC0;
1189+
1190+
esp_err_t ret = esp_ble_gap_set_rand_addr(rand_addr);
1191+
if (ret != ESP_OK)
1192+
{
1193+
ChipLogError(DeviceLayer, "Failed to set random address: %s", esp_err_to_name(ret));
1194+
return ret;
1195+
}
1196+
1197+
return ESP_OK;
1198+
}
1199+
#endif
1200+
11391201
CHIP_ERROR BLEManagerImpl::ConfigureAdvertisingData(void)
11401202
{
11411203
CHIP_ERROR err;
@@ -1161,6 +1223,27 @@ CHIP_ERROR BLEManagerImpl::ConfigureAdvertisingData(void)
11611223
ExitNow();
11621224
}
11631225

1226+
#if CHIP_DEVICE_CONFIG_BLE_EXT_ADVERTISING
1227+
// Check for extended advertisement interval and redact VID/PID if past the initial period.
1228+
if (mFlags.Has(Flags::kExtAdvertisingEnabled))
1229+
{
1230+
deviceIdInfo.SetVendorId(0);
1231+
deviceIdInfo.SetProductId(0);
1232+
deviceIdInfo.SetExtendedAnnouncementFlag(true);
1233+
}
1234+
#endif
1235+
1236+
#if CHIP_ENABLE_ADDITIONAL_DATA_ADVERTISING
1237+
if (!mFlags.Has(Flags::kExtAdvertisingEnabled))
1238+
{
1239+
deviceIdInfo.SetAdditionalDataFlag(true);
1240+
}
1241+
else
1242+
{
1243+
deviceIdInfo.SetAdditionalDataFlag(false);
1244+
}
1245+
#endif
1246+
11641247
memset(advData, 0, sizeof(advData));
11651248
advData[index++] = 0x02; // length
11661249
advData[index++] = CHIP_ADV_DATA_TYPE_FLAGS; // AD type : flags
@@ -1190,12 +1273,69 @@ CHIP_ERROR BLEManagerImpl::ConfigureAdvertisingData(void)
11901273
ExitNow();
11911274
}
11921275

1276+
#ifndef CONFIG_IDF_TARGET_ESP32
1277+
bluedroid_set_random_address();
1278+
#endif
1279+
11931280
mFlags.Set(Flags::kControlOpInProgress);
11941281

11951282
exit:
11961283
return err;
11971284
}
11981285

1286+
// TODO: Fix the ShutDown flow
1287+
void BLEManagerImpl::DeinitESPBleLayer()
1288+
{
1289+
esp_err_t err;
1290+
1291+
err = esp_ble_gatts_app_unregister(mAppIf);
1292+
if (err != ESP_OK)
1293+
{
1294+
ChipLogError(DeviceLayer, "Unregister failed: %d", err);
1295+
return;
1296+
}
1297+
1298+
err = esp_bluedroid_disable();
1299+
if (err != ESP_OK)
1300+
{
1301+
ChipLogError(DeviceLayer, "esp_bluedroid_disable() failed: %d", err);
1302+
return;
1303+
}
1304+
1305+
err = esp_bluedroid_deinit();
1306+
if (err != ESP_OK)
1307+
{
1308+
ChipLogError(DeviceLayer, "esp_bluedroid_deinit() failed: %d", err);
1309+
return;
1310+
}
1311+
1312+
err = esp_bt_controller_disable();
1313+
if (err != ESP_OK)
1314+
{
1315+
ChipLogError(DeviceLayer, "esp_bt_controller_disable() failed: %d", err);
1316+
return;
1317+
}
1318+
1319+
err = esp_bt_controller_deinit();
1320+
if (err != ESP_OK)
1321+
{
1322+
ChipLogError(DeviceLayer, "esp_bt_controller_deinit() failed: %d", err);
1323+
return;
1324+
}
1325+
1326+
#ifdef CONFIG_IDF_TARGET_ESP32
1327+
VerifyOrReturn(ESP_OK == esp_bt_mem_release(ESP_BT_MODE_BTDM), ChipLogError(DeviceLayer, "Failed to release bt memory"));
1328+
#elif defined(CONFIG_IDF_TARGET_ESP32C2) || defined(CONFIG_IDF_TARGET_ESP32C3) || defined(CONFIG_IDF_TARGET_ESP32S3) || \
1329+
defined(CONFIG_IDF_TARGET_ESP32H2) || defined(CONFIG_IDF_TARGET_ESP32C6)
1330+
VerifyOrReturn(ESP_OK == esp_bt_mem_release(ESP_BT_MODE_BLE), ChipLogError(DeviceLayer, "Failed to release bt memory"));
1331+
#endif
1332+
ChipLogProgress(DeviceLayer, "BLE memory reclaimed");
1333+
1334+
ChipDeviceEvent event;
1335+
event.Type = DeviceEventType::kBLEDeinitialized;
1336+
VerifyOrDo(CHIP_NO_ERROR == PlatformMgr().PostEvent(&event), ChipLogError(DeviceLayer, "Failed to post BLE deinit event"));
1337+
}
1338+
11991339
CHIP_ERROR BLEManagerImpl::StartAdvertising(void)
12001340
{
12011341
CHIP_ERROR err;
@@ -1226,8 +1366,23 @@ CHIP_ERROR BLEManagerImpl::StartAdvertising(void)
12261366
}
12271367
else
12281368
{
1369+
#if CHIP_DEVICE_CONFIG_BLE_EXT_ADVERTISING
1370+
if (!mFlags.Has(Flags::kExtAdvertisingEnabled))
1371+
{
1372+
advertParams.adv_int_min = CHIP_DEVICE_CONFIG_BLE_SLOW_ADVERTISING_INTERVAL_MIN;
1373+
advertParams.adv_int_max = CHIP_DEVICE_CONFIG_BLE_SLOW_ADVERTISING_INTERVAL_MAX;
1374+
}
1375+
else
1376+
{
1377+
advertParams.adv_int_min = CHIP_DEVICE_CONFIG_BLE_EXT_ADVERTISING_INTERVAL_MIN;
1378+
advertParams.adv_int_max = CHIP_DEVICE_CONFIG_BLE_EXT_ADVERTISING_INTERVAL_MAX;
1379+
}
1380+
#else
1381+
12291382
advertParams.adv_int_min = CHIP_DEVICE_CONFIG_BLE_SLOW_ADVERTISING_INTERVAL_MIN;
12301383
advertParams.adv_int_max = CHIP_DEVICE_CONFIG_BLE_SLOW_ADVERTISING_INTERVAL_MAX;
1384+
1385+
#endif
12311386
}
12321387

12331388
ChipLogProgress(DeviceLayer, "Configuring CHIPoBLE advertising (interval %" PRIu32 " ms, %sconnectable, device name %s)",

0 commit comments

Comments
 (0)